📄 fuzzy11a.lst
字号:
00103 * FCB $80+8*OUTy+LABc ;Then output YY is label CCC
00104
00105 A b664 b664 A RULE_START EQU * ;Start of first rule
00106 * Example rule: If TEMPERATURE is VERY_HOT and DAYS_SINCE_RAIN is LONG
00107 * Then WATERING_TIME is INCREASE_GREATLY
00108 A b664 221b85 A RULE_1 FCB 2+(8*4),3+(8*3),$80+(8*0)+5
00109 A b667 ff A END_OF_RULE FCB $FF
00110
00111 ***** Fuzzy Inferrence Engine Starts Here
00112 *
00113 A b66b ORG $B66B
00114 A b66b ce 0008 A INFER_TOP LDX #FUZ_OUTS ;Point at first fuzzy output
00115 A b66e 86 20 A LDAA #32 ;32 fuzzy outputs
00116 A b670 6f 00 A CLR_OUTS CLR 0,X ;Clear a fuzzy output
00117 A b672 08 INX ;Point at next
00118 A b673 4a DECA ;Loop index
00119 A b674 26 fa b670 BNE CLR_OUTS ;Continue till all fuzzy outs 0
00120 A b676 18ce b664 A LDY #RULE_START ;Point to start of 1st rule
00121 A b67a 86 ff A RULE_TOP LDAA #$FF ;Begin processing rule string
00122 A b67c 97 2c A STAA LOWEST_IF ;Will hold grade of min if part
00123 A b67e 18e6 00 A IF_LOOP LDAB 0,Y ;Get rule byte 00AA AXXX; If X is A
00124 A b681 2b 63 b6e6 BMI THEN_LOOP ;If MSB=1, exit to then loop
00125 A b683 ce 0000 A LDX #CURRENT_INS ;Point at current input data area
00126 A b686 c4 07 A ANDB #$07 ;Save only input number
00127 A b688 37 PSHB ;Will need input # again
00128 A b689 3a ABX ;Point to specific input data
00129 A b68a a6 00 A LDAA 0,X ;Get current input data
00130 A b68c ce b600 A LDX #IN_MF_PTRS ;Point at offsets for input MFs
00131 A b68f 33 PULB ;Recover input number 0000 0XXX
00132 A b690 3a ABX ;Point at pointer for this input #
00133 A b691 ee 00 A LDX 0,X ;Get pointer into MF data area
00134 A b693 18e6 00 A LDAB 0,Y ;Get rule if part 00AA AXXX
00135 A b696 c4 38 A ANDB #$38 ;00AA A000 is 8 times AAA
00136 A b698 54 LSRB ;000A AA00 4 times AAA
00137 A b699 3a ABX ;X points at MF points & slopes
00138 A b69a a1 00 A CMPA 0,X ;Compare input data to MF pt1
00139 A b69c 24 03 b6a1 BHS NOT_SEG0 ;Branch if not segment zero
00140 A b69e 5f CLRB ;In seg 0 grade is zero
00141 A b69f 20 25 b6c6 BRA HAVE_GRADE ;Have grade of membership
00142 A b6a1 a1 02 A NOT_SEG0 CMPA 2,X ;Compare input data to MF pt2
00143 A b6a3 22 11 b6b6 BHI IS_SEG2 ;Branch if segment two
M68HC11 Portable Cross Assembler 0.05 FUZZY11A.ASM Page 8
Thu Oct 10 16:08:33 1991
Options - MD,MC,NOG,NOU,W,MEX,CL,FMT,O
LINE S PC OPCO OPERANDS S LABEL MNEMO OPERANDS COMMENT
00144 A b6a5 e6 01 A LDAB 1,X ;Slope1 -> B
00145 A b6a7 27 09 b6b2 BEQ JAM_FF ;If vert slope, jam $FF
00146 A b6a9 a0 00 A SUBA 0,X ;Input value - pt1 -> A
00147 A b6ab 3d MUL ;Grade in B if D < $100
00148 A b6ac 1a83 0100 A CPD #$100 ;Check for overflow
00149 A b6b0 25 14 b6c6 BLO HAVE_GRADE ;If < $100 grade OK in B
00150 A b6b2 c6 ff A JAM_FF LDAB #$FF ;Else limit B to $FF
00151 A b6b4 20 10 b6c6 BRA HAVE_GRADE ;Have grade of membership
00152 A b6b6 e6 03 A IS_SEG2 LDAB 3,X ;Slope2 -> B
00153 A b6b8 a0 02 A SUBA 2,X ;Input value - pt2 -> A
00154 A b6ba 3d MUL ;Grade in B if D < $100
00155 A b6bb 1a83 0100 A CPD #$100 ;Check for overflow
00156 A b6bf 25 02 b6c3 BLO B_OK ;If < $100 value in B OK
00157 A b6c1 c6 ff A LDAB #$FF ;Else limit B to $FF
00158 A b6c3 86 ff A B_OK LDAA #$FF ;Grade should be $FF - (B)
00159 A b6c5 10 SBA ;Grade of membership in B
00160 A b6c6 d1 2c A HAVE_GRADE CMPB LOWEST_IF ;Is grade lowest so far ?
00161 A b6c8 24 18 b6e2 BHS NOT_LOWR ;Branch if not lower
00162 A b6ca d7 2c A STAB LOWEST_IF ;If lower, replace lowest if
00163 A b6cc 26 14 b6e2 BNE NOT_LOWR ;Skip ahead if not zero
00164 A b6ce 1808 FIND_THEN INY ;Adv rule pointer to then part
00165 A b6d0 18e6 00 A LDAB 0,Y ;Get next rule byte
00166 A b6d3 2a f9 b6ce BPL FIND_THEN ;MSB set means its a then part
00167 A b6d5 1808 FIND_IF INY ;Adv rule pointer to if part
00168 A b6d7 18e6 00 A LDAB 0,Y ;Get next rule byte
00169 A b6da 2a 9e b67a BPL RULE_TOP ;MSB clear means its an if part
00170 A b6dc c1 ff A CMPB #$FF ;$FF is no more rules marker
00171 A b6de 26 f5 b6d5 BNE FIND_IF ;Continue looking for if or $FF
00172 A b6e0 20 20 b702 BRA DEFUZ ;When all rules done, go defuzzify
00173 A b6e2 1808 NOT_LOWR INY ;Point to next rule byte
00174 A b6e4 20 98 b67e BRA IF_LOOP ;Continue for all if parts
00175 A b6e6 ce 0008 A THEN_LOOP LDX #FUZ_OUTS ;Point at fuzzy outputs
00176 A b6e9 c4 1f A ANDB #$1F ;Save 8 times out # + label #
00177 A b6eb 3a ABX ;X points at fuzzy output
00178 A b6ec 96 2c A LDAA LOWEST_IF ;Grade of membership for rule
00179 A b6ee a1 00 A CMPA 0,X ;Compare to fuzzy output
00180 A b6f0 25 02 b6f4 BLO NOT_HIER ;Branch if not higher
00181 A b6f2 a7 00 A STAA 0,X ;Grade is higher so update
00182 A b6f4 1808 NOT_HIER INY ;Point to next rule byte
00183 A b6f6 18e6 00 A LDAB 0,Y ;Get rule byte
00184 A b6f9 2b 03 b6fe BMI CHK_END ;If MSB=0 its a new rule
00185 A b6fb 7e b67a A JMP RULE_TOP ;Else process next rule byte
00186 A b6fe c1 ff A CHK_END CMPB #$FF ;Check for end of rules flag
00187 A b700 26 e4 b6e6 BNE THEN_LOOP ;If not $FF, must be a then part
00188 A b702 18ce b644 A DEFUZ LDY #SGLTN_POS ;Point at 1st output singleton
00189 A b706 ce 0008 A LDX #FUZ_OUTS ;Point at 1st fuzzy output
00190 A b709 7f 0032 A CLR COGDEX ;Loop index will run from 0->4
00191 A b70c c6 08 A COG_LOOP LDAB #8 ;8 fuzzy outs per COG output
00192 A b70e d7 33 A STAB SUMDEX ;Inner loop runs 8->0
00193 A b710 cc 0000 A LDD #$0000 ;Used for quicker clears
00194 A b713 dd 2d A STD SUM_OF_FUZ ;Sum of fuzzy outputs
00195 A b715 dd 30 A STD SUM_OF_PROD+1 ;Low 16-bits of sum of products
M68HC11 Portable Cross Assembler 0.05 FUZZY11A.ASM Page 9
Thu Oct 10 16:08:33 1991
Options - MD,MC,NOG,NOU,W,MEX,CL,FMT,O
LINE S PC OPCO OPERANDS S LABEL MNEMO OPERANDS COMMENT
00196 A b717 97 2f A STAA SUM_OF_PROD ;Upper 8-bits
00197 A b719 e6 00 A SUM_LOOP LDAB 0,X ;Get a fuzzy output
00198 A b71b 4f CLRA ;Clear upper 8-bits
00199 A b71c d3 2d A ADDD SUM_OF_FUZ ;Add to sum of fuzzy outputs
00200 A b71e dd 2d A STD SUM_OF_FUZ ;Update RAM variable
00201 A b720 a6 00 A LDAA 0,X ;Get fuzzy output again
00202 A b722 18e6 00 A LDAB 0,Y ;Get Output singleton position
00203 A b725 3d MUL ;Position times weight
00204 A b726 d3 30 A ADDD SUM_OF_PROD+1 ;Low 16-bits of sum of products
00205 A b728 dd 30 A STD SUM_OF_PROD+1 ;Update low 16-bits
00206 A b72a 96 2f A LDAA SUM_OF_PROD ;Upper 8-bits
00207 A b72c 89 00 A ADCA #0 ;Add carry from 16-bit add
00208 A b72e 97 2f A STAA SUM_OF_PROD ;Upper 8-bits of 24-bit sum
00209 A b730 1808 INY ;Point at next singleton pos.
00210 A b732 08 INX ;Point at next fuzzy output
00211 A b733 7a 0033 A DEC SUMDEX ;Inner loop index
00212 A b736 26 e1 b719 BNE SUM_LOOP ;For all labels this output
00213 A b738 3c PSHX ;Save index for now
00214 A b739 4f CLRA ;In case divide by zero
00215 A b73a de 2d A LDX SUM_OF_FUZ ;Demominator for divide
00216 A b73c 27 18 b756 BEQ SAV_OUT ;Branch if denominator is 0
00217 A b73e 7d 002f A TST SUM_OF_PROD ;See if more than 16-bit
00218 A b741 26 07 b74a BNE NUM_BIG ;If not zero, # is > 16-bits
00219 A b743 dc 30 A LDD SUM_OF_PROD+1 ;Numerator for divide
00220 A b745 02 IDIV ;Result in low 8-bits of X
00221 A b746 8f XGDX ;Result now in B
00222 A b747 17 TBA ;Move result to A
00223 A b748 20 0c b756 BRA SAV_OUT ;Go save output
00224 A b74a dc 2f A NUM_BIG LDD SUM_OF_PROD ;Numerator upper 16 of 24-bit
00225 A b74c 7d 0031 A TST SUM_OF_PROD+2 ;Check for rounding error
00226 A b74f 2a 03 b754 BPL NO_ROUND ;If MSB clear, don't round
00227 A b751 c3 0001 A ADDD #1 ;Round numerator up 1
00228 A b754 03 NO_ROUND FDIV ;D/X -> X, use upper 8 of 16
00229 A b755 8f XGDX ;Result now in A
00230 A b756 ce 0028 A SAV_OUT LDX #COG_OUTS ;Point to 1st defuz output
00231 A b759 d6 32 A LDAB COGDEX ;Curent output number
00232 A b75b 3a ABX ;Point to correct output
00233 A b75c a7 00 A STAA 0,X ;Update defuzzified output
00234 A b75e 38 PULX ;Recover index
00235 A b75f 5c INCB ;Increment loop index
00236 A b760 d7 32 A STAB COGDEX ;Update
00237 A b762 c1 04 A CMPB #4 ;Done with all four outs?
00238 A b764 26 a6 b70c BNE COG_LOOP ;If not, continue loop
00239
00240 * Inference engine has completed one pass of all rules.
00241
***** warning 24: END statement is missing
M68HC11 Portable Cross Assembler 0.05 Page 10
Thu Oct 10 16:08:33 1991
Total number of errors: 0
Total number of warnings: 1
Total number of lines: 241
Number of bytes in section ASCT: 407
Number of bytes in program: 407