%% $RCSfile: sdf2t.tlc,v $ %% $Revision: 1.7 $ %% $Date: 1999/03/24 14:52:58 $ %% %% Don Orofino and Pete Szpak %% December 5, 1997 %% Copyright (c) 1995-1999 The MathWorks, Inc. All Rights Reserved. %% %% Abstract: Dot product block target file. %implements sdf2t "C" %function MAX(a,b) void %return ((a)>(b)?(a):(b)) %endfunction %function MIN(a,b) void %return ((a)<(b)?(a):(b)) %endfunction %% Function: BlockInstanceSetup =============================================== %% %% Abstract: %% Rename the S-Function parameter for easy reference. %% %function BlockInstanceSetup(block, system) void %% % % % %% %if RWork[0] > 0 % %endif %% %assign LenNUM = SIZE(NUM.Value,0) * SIZE(NUM.Value,1) %assign LenDEN = SIZE(DEN.Value,0) * SIZE(DEN.Value,1) %assign LenMIN = MIN(LenNUM, LenDEN) %assign NumCHANS = LibDataInputPortWidth(0) %assign NumDELAYS = MAX(LenNUM, LenDEN) - 1 %assign NumELE = NumCHANS * NumDELAYS %assign block = block + LenNUM %assign block = block + LenDEN %assign block = block + LenMIN %assign block = block + NumCHANS %assign block = block + NumDELAYS %assign block = block + NumELE %endfunction %% BlockInstanceSetup %% Function: InitializeConditions ============================================= %% %% Abstract: %% Initialize the RWork vector (Buffer) to the initial values specified. %% Note that the IWork is memset to zero in the registration function, %% however we need to initialize it to zero again here, because this block %% might be used inside an enabled subsystem that resets on disable. %% %function InitializeConditions(block, system) Output /* % Block: % (%) */ { %% %assign numIC = SIZE(IC.Value,0) * SIZE(IC.Value,1) %% %if numIC == 0 %% No IC's given -- set them all to zero %assign rollVars = ["/DlyBuf"] %assign rollRegions = [0:%] %roll sigIdx = rollRegions, lcv = RollThreshold, block, "Roller", \ rollVars % = 0.0; %endroll %% %elseif numIC == 1 %% Scalar expansion of single IC %assign rollVars = ["/DlyBuf"] %assign rollRegions = [0:%] %roll sigIdx = rollRegions, lcv = RollThreshold, block, "Roller", \ rollVars % = %; %endroll %% %elseif numIC == NumDELAYS %% Repeat single column of IC's for each channel real_T *pIC = %; real_T *pDlyBuf = &%; %assign rollVars = ["/DlyBuf"] %assign rollRegions = [0:%] %assign rollThreshold = 3 %roll sigIdx = rollRegions, lcv = rollThreshold, block, "Roller", \ rollVars memcpy((void *)pDlyBuf, (void *)pIC, %*sizeof(real_T)); pDlyBuf += %; %endroll %% %else %% Matrix of IC's %% Copy each columns of IC's into each channel real_T *pDlyBuf = &%; memcpy(pDlyBuf, %,%*sizeof(real_T)); %endif } %endfunction %% InitializeConditions %% Function: Outputs ========================================================== %% %function Outputs(block, system) Output /* % Block: % */ { %if Connections.InputPortContiguous[0] == "no" %% Setup pointer indices to discontiguous inputs static real_T *uPtrs[] = { %foreach sigIdx=NumCHANS % \ %if sigIdx != NumCHANS-1 , %% <-- That's a comma! %endif %endforeach }; %endif %% real_T *tmpDL = &%; /* Start of buffer */ real_T *tmpDR = tmpDL; %% %% Define output vector: %% real_T *y = %; %% /* Loop over each input channel: */ %% %if NumCHANS>1 int_T iChans; for(iChans=0; iChans<%; iChans++) { %endif %% real_T *tmpNUM = %; real_T *tmpDEN = %; %if Connections.InputPortContiguous[0] == "no" real_T in = *uPtrs[iChans]; %else real_T in = %; %endif real_T out; int_T iCoef; /* Compute filter output value: */ out = in * *tmpNUM++; %if NumDELAYS > 0 out += *tmpDR++; /* No delays present if LenMIN=1 */ %endif %% %% Only scale output if first denominator term is non-unity: %% out /= *tmpDEN++; /* Scale filter output accordingly */ /* Record filter output */ %% %% Could have done this: %% %% % = out; %% %% Instead, we'll do this: %% *y++ = out; %% out = -out; /* We can use addition uniformly below */ %if LenNUM != LenDEN /* Unequal length coefficient vectors */ %if LenMIN>1 iCoef = %; while(--iCoef > 0) { *tmpDL++ = *tmpDR++ + in * *tmpNUM++ + out * *tmpDEN++; } %endif %% %if LenNUM > LenDEN %if LenNUM - LenMIN > 1 iCoef = %; /* More numerator coeffs */ while(--iCoef > 0) { *tmpDL++ = *tmpDR++ + in * *tmpNUM++; } %endif *tmpDL++ = in * *tmpNUM++; %else %if LenDEN - LenMIN > 1 iCoef = %; /* More denominator coeffs */ while(--iCoef > 0) { *tmpDL++ = *tmpDR++ + out * *tmpDEN++; } %endif *tmpDL++ = out * *tmpDEN++; %endif %else /* Equal length coefficient vectors */ %% Make sure there's at least one polynomial entry %if LenNUM > 1 %% or LenDEN > 1 iCoef = %; while(--iCoef > 0) { *tmpDL++ = *tmpDR++ + in * *tmpNUM++ + out * *tmpDEN++; } *tmpDL++ = in * *tmpNUM++ + out * *tmpDEN++; %endif %endif /* At this point, tmpDL and tmpDR correctly point */ /* to the start of the next delay buffer segment */ %if NumCHANS>1 } %endif } %endfunction %% [EOF] sdf2t.tlc