@@ -1063,6 +1063,139 @@ static int fsl_asrc_get_fifo_addr(u8 dir, enum asrc_pair_index index)
10631063 return REG_ASRDx (dir , index );
10641064}
10651065
1066+ /* Get sample numbers in FIFO */
1067+ static unsigned int fsl_asrc_get_output_fifo_size (struct fsl_asrc_pair * pair )
1068+ {
1069+ struct fsl_asrc * asrc = pair -> asrc ;
1070+ enum asrc_pair_index index = pair -> index ;
1071+ u32 val ;
1072+
1073+ regmap_read (asrc -> regmap , REG_ASRFST (index ), & val );
1074+
1075+ val &= ASRFSTi_OUTPUT_FIFO_MASK ;
1076+
1077+ return val >> ASRFSTi_OUTPUT_FIFO_SHIFT ;
1078+ }
1079+
1080+ static int fsl_asrc_m2m_prepare (struct fsl_asrc_pair * pair )
1081+ {
1082+ struct fsl_asrc_pair_priv * pair_priv = pair -> private ;
1083+ struct fsl_asrc * asrc = pair -> asrc ;
1084+ struct device * dev = & asrc -> pdev -> dev ;
1085+ struct asrc_config config ;
1086+ int ret ;
1087+
1088+ /* fill config */
1089+ config .pair = pair -> index ;
1090+ config .channel_num = pair -> channels ;
1091+ config .input_sample_rate = pair -> rate [IN ];
1092+ config .output_sample_rate = pair -> rate [OUT ];
1093+ config .input_format = pair -> sample_format [IN ];
1094+ config .output_format = pair -> sample_format [OUT ];
1095+ config .inclk = INCLK_NONE ;
1096+ config .outclk = OUTCLK_ASRCK1_CLK ;
1097+
1098+ pair_priv -> config = & config ;
1099+ ret = fsl_asrc_config_pair (pair , true);
1100+ if (ret ) {
1101+ dev_err (dev , "failed to config pair: %d\n" , ret );
1102+ return ret ;
1103+ }
1104+
1105+ pair -> first_convert = 1 ;
1106+
1107+ return 0 ;
1108+ }
1109+
1110+ static int fsl_asrc_m2m_start (struct fsl_asrc_pair * pair )
1111+ {
1112+ if (pair -> first_convert ) {
1113+ fsl_asrc_start_pair (pair );
1114+ pair -> first_convert = 0 ;
1115+ }
1116+ /*
1117+ * Clear DMA request during the stall state of ASRC:
1118+ * During STALL state, the remaining in input fifo would never be
1119+ * smaller than the input threshold while the output fifo would not
1120+ * be bigger than output one. Thus the DMA request would be cleared.
1121+ */
1122+ fsl_asrc_set_watermarks (pair , ASRC_FIFO_THRESHOLD_MIN ,
1123+ ASRC_FIFO_THRESHOLD_MAX );
1124+
1125+ /* Update the real input threshold to raise DMA request */
1126+ fsl_asrc_set_watermarks (pair , ASRC_M2M_INPUTFIFO_WML ,
1127+ ASRC_M2M_OUTPUTFIFO_WML );
1128+
1129+ return 0 ;
1130+ }
1131+
1132+ static int fsl_asrc_m2m_stop (struct fsl_asrc_pair * pair )
1133+ {
1134+ if (!pair -> first_convert ) {
1135+ fsl_asrc_stop_pair (pair );
1136+ pair -> first_convert = 1 ;
1137+ }
1138+
1139+ return 0 ;
1140+ }
1141+
1142+ /* calculate capture data length according to output data length and sample rate */
1143+ static int fsl_asrc_m2m_calc_out_len (struct fsl_asrc_pair * pair , int input_buffer_length )
1144+ {
1145+ unsigned int in_width , out_width ;
1146+ unsigned int channels = pair -> channels ;
1147+ unsigned int in_samples , out_samples ;
1148+ unsigned int out_length ;
1149+
1150+ in_width = snd_pcm_format_physical_width (pair -> sample_format [IN ]) / 8 ;
1151+ out_width = snd_pcm_format_physical_width (pair -> sample_format [OUT ]) / 8 ;
1152+
1153+ in_samples = input_buffer_length / in_width / channels ;
1154+ out_samples = pair -> rate [OUT ] * in_samples / pair -> rate [IN ];
1155+ out_length = (out_samples - ASRC_OUTPUT_LAST_SAMPLE ) * out_width * channels ;
1156+
1157+ return out_length ;
1158+ }
1159+
1160+ static int fsl_asrc_m2m_get_maxburst (u8 dir , struct fsl_asrc_pair * pair )
1161+ {
1162+ struct fsl_asrc * asrc = pair -> asrc ;
1163+ struct fsl_asrc_priv * asrc_priv = asrc -> private ;
1164+ int wml = (dir == IN ) ? ASRC_M2M_INPUTFIFO_WML : ASRC_M2M_OUTPUTFIFO_WML ;
1165+
1166+ if (!asrc_priv -> soc -> use_edma )
1167+ return wml * pair -> channels ;
1168+ else
1169+ return 1 ;
1170+ }
1171+
1172+ static int fsl_asrc_m2m_get_cap (struct fsl_asrc_m2m_cap * cap )
1173+ {
1174+ cap -> fmt_in = FSL_ASRC_FORMATS ;
1175+ cap -> fmt_out = FSL_ASRC_FORMATS | SNDRV_PCM_FMTBIT_S8 ;
1176+
1177+ cap -> rate_in = supported_asrc_rate ;
1178+ cap -> rate_in_count = ARRAY_SIZE (supported_asrc_rate );
1179+ cap -> rate_out = supported_asrc_rate ;
1180+ cap -> rate_out_count = ARRAY_SIZE (supported_asrc_rate );
1181+ cap -> chan_min = 1 ;
1182+ cap -> chan_max = 10 ;
1183+
1184+ return 0 ;
1185+ }
1186+
1187+ static int fsl_asrc_m2m_pair_resume (struct fsl_asrc_pair * pair )
1188+ {
1189+ struct fsl_asrc * asrc = pair -> asrc ;
1190+ int i ;
1191+
1192+ for (i = 0 ; i < pair -> channels * 4 ; i ++ )
1193+ regmap_write (asrc -> regmap , REG_ASRDI (pair -> index ), 0 );
1194+
1195+ pair -> first_convert = 1 ;
1196+ return 0 ;
1197+ }
1198+
10661199static int fsl_asrc_runtime_resume (struct device * dev );
10671200static int fsl_asrc_runtime_suspend (struct device * dev );
10681201
@@ -1147,6 +1280,15 @@ static int fsl_asrc_probe(struct platform_device *pdev)
11471280 asrc -> get_fifo_addr = fsl_asrc_get_fifo_addr ;
11481281 asrc -> pair_priv_size = sizeof (struct fsl_asrc_pair_priv );
11491282
1283+ asrc -> m2m_prepare = fsl_asrc_m2m_prepare ;
1284+ asrc -> m2m_start = fsl_asrc_m2m_start ;
1285+ asrc -> m2m_stop = fsl_asrc_m2m_stop ;
1286+ asrc -> get_output_fifo_size = fsl_asrc_get_output_fifo_size ;
1287+ asrc -> m2m_calc_out_len = fsl_asrc_m2m_calc_out_len ;
1288+ asrc -> m2m_get_maxburst = fsl_asrc_m2m_get_maxburst ;
1289+ asrc -> m2m_pair_resume = fsl_asrc_m2m_pair_resume ;
1290+ asrc -> m2m_get_cap = fsl_asrc_m2m_get_cap ;
1291+
11501292 if (of_device_is_compatible (np , "fsl,imx35-asrc" )) {
11511293 asrc_priv -> clk_map [IN ] = input_clk_map_imx35 ;
11521294 asrc_priv -> clk_map [OUT ] = output_clk_map_imx35 ;
@@ -1242,6 +1384,12 @@ static int fsl_asrc_probe(struct platform_device *pdev)
12421384 goto err_pm_get_sync ;
12431385 }
12441386
1387+ ret = fsl_asrc_m2m_init (asrc );
1388+ if (ret ) {
1389+ dev_err (& pdev -> dev , "failed to init m2m device %d\n" , ret );
1390+ return ret ;
1391+ }
1392+
12451393 return 0 ;
12461394
12471395err_pm_get_sync :
@@ -1254,6 +1402,10 @@ static int fsl_asrc_probe(struct platform_device *pdev)
12541402
12551403static void fsl_asrc_remove (struct platform_device * pdev )
12561404{
1405+ struct fsl_asrc * asrc = dev_get_drvdata (& pdev -> dev );
1406+
1407+ fsl_asrc_m2m_exit (asrc );
1408+
12571409 pm_runtime_disable (& pdev -> dev );
12581410 if (!pm_runtime_status_suspended (& pdev -> dev ))
12591411 fsl_asrc_runtime_suspend (& pdev -> dev );
@@ -1355,10 +1507,29 @@ static int fsl_asrc_runtime_suspend(struct device *dev)
13551507 return 0 ;
13561508}
13571509
1510+ static int fsl_asrc_suspend (struct device * dev )
1511+ {
1512+ struct fsl_asrc * asrc = dev_get_drvdata (dev );
1513+ int ret ;
1514+
1515+ fsl_asrc_m2m_suspend (asrc );
1516+ ret = pm_runtime_force_suspend (dev );
1517+ return ret ;
1518+ }
1519+
1520+ static int fsl_asrc_resume (struct device * dev )
1521+ {
1522+ struct fsl_asrc * asrc = dev_get_drvdata (dev );
1523+ int ret ;
1524+
1525+ ret = pm_runtime_force_resume (dev );
1526+ fsl_asrc_m2m_resume (asrc );
1527+ return ret ;
1528+ }
1529+
13581530static const struct dev_pm_ops fsl_asrc_pm = {
1359- SET_RUNTIME_PM_OPS (fsl_asrc_runtime_suspend , fsl_asrc_runtime_resume , NULL )
1360- SET_SYSTEM_SLEEP_PM_OPS (pm_runtime_force_suspend ,
1361- pm_runtime_force_resume )
1531+ RUNTIME_PM_OPS (fsl_asrc_runtime_suspend , fsl_asrc_runtime_resume , NULL )
1532+ SYSTEM_SLEEP_PM_OPS (fsl_asrc_suspend , fsl_asrc_resume )
13621533};
13631534
13641535static const struct fsl_asrc_soc_data fsl_asrc_imx35_data = {
@@ -1396,7 +1567,7 @@ static struct platform_driver fsl_asrc_driver = {
13961567 .driver = {
13971568 .name = "fsl-asrc" ,
13981569 .of_match_table = fsl_asrc_ids ,
1399- .pm = & fsl_asrc_pm ,
1570+ .pm = pm_ptr ( & fsl_asrc_pm ) ,
14001571 },
14011572};
14021573module_platform_driver (fsl_asrc_driver );
0 commit comments