clipsruby 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/ext/clipsruby/agenda.c +1373 -0
- data/ext/clipsruby/agenda.h +169 -0
- data/ext/clipsruby/analysis.c +1142 -0
- data/ext/clipsruby/analysis.h +61 -0
- data/ext/clipsruby/argacces.c +526 -0
- data/ext/clipsruby/argacces.h +77 -0
- data/ext/clipsruby/bload.c +884 -0
- data/ext/clipsruby/bload.h +94 -0
- data/ext/clipsruby/bmathfun.c +557 -0
- data/ext/clipsruby/bmathfun.h +66 -0
- data/ext/clipsruby/bsave.c +634 -0
- data/ext/clipsruby/bsave.h +130 -0
- data/ext/clipsruby/classcom.c +976 -0
- data/ext/clipsruby/classcom.h +115 -0
- data/ext/clipsruby/classexm.c +1376 -0
- data/ext/clipsruby/classexm.h +97 -0
- data/ext/clipsruby/classfun.c +1392 -0
- data/ext/clipsruby/classfun.h +164 -0
- data/ext/clipsruby/classinf.c +1245 -0
- data/ext/clipsruby/classinf.h +94 -0
- data/ext/clipsruby/classini.c +843 -0
- data/ext/clipsruby/classini.h +75 -0
- data/ext/clipsruby/classpsr.c +957 -0
- data/ext/clipsruby/classpsr.h +73 -0
- data/ext/clipsruby/clips.h +133 -0
- data/ext/clipsruby/clipsruby.c +619 -0
- data/ext/clipsruby/clsltpsr.c +931 -0
- data/ext/clipsruby/clsltpsr.h +72 -0
- data/ext/clipsruby/commline.c +1217 -0
- data/ext/clipsruby/commline.h +131 -0
- data/ext/clipsruby/conscomp.c +1593 -0
- data/ext/clipsruby/conscomp.h +150 -0
- data/ext/clipsruby/constant.h +264 -0
- data/ext/clipsruby/constrct.c +1090 -0
- data/ext/clipsruby/constrct.h +216 -0
- data/ext/clipsruby/constrnt.c +554 -0
- data/ext/clipsruby/constrnt.h +132 -0
- data/ext/clipsruby/crstrtgy.c +1088 -0
- data/ext/clipsruby/crstrtgy.h +85 -0
- data/ext/clipsruby/cstrcbin.c +185 -0
- data/ext/clipsruby/cstrcbin.h +61 -0
- data/ext/clipsruby/cstrccmp.h +43 -0
- data/ext/clipsruby/cstrccom.c +1791 -0
- data/ext/clipsruby/cstrccom.h +115 -0
- data/ext/clipsruby/cstrcpsr.c +835 -0
- data/ext/clipsruby/cstrcpsr.h +97 -0
- data/ext/clipsruby/cstrnbin.c +282 -0
- data/ext/clipsruby/cstrnbin.h +55 -0
- data/ext/clipsruby/cstrnchk.c +826 -0
- data/ext/clipsruby/cstrnchk.h +91 -0
- data/ext/clipsruby/cstrncmp.c +238 -0
- data/ext/clipsruby/cstrncmp.h +57 -0
- data/ext/clipsruby/cstrnops.c +1176 -0
- data/ext/clipsruby/cstrnops.h +47 -0
- data/ext/clipsruby/cstrnpsr.c +1394 -0
- data/ext/clipsruby/cstrnpsr.h +88 -0
- data/ext/clipsruby/cstrnutl.c +564 -0
- data/ext/clipsruby/cstrnutl.h +54 -0
- data/ext/clipsruby/default.c +454 -0
- data/ext/clipsruby/default.h +57 -0
- data/ext/clipsruby/defins.c +971 -0
- data/ext/clipsruby/defins.h +127 -0
- data/ext/clipsruby/developr.c +677 -0
- data/ext/clipsruby/developr.h +69 -0
- data/ext/clipsruby/dffctbin.c +477 -0
- data/ext/clipsruby/dffctbin.h +76 -0
- data/ext/clipsruby/dffctbsc.c +308 -0
- data/ext/clipsruby/dffctbsc.h +72 -0
- data/ext/clipsruby/dffctcmp.c +297 -0
- data/ext/clipsruby/dffctcmp.h +44 -0
- data/ext/clipsruby/dffctdef.c +364 -0
- data/ext/clipsruby/dffctdef.h +104 -0
- data/ext/clipsruby/dffctpsr.c +179 -0
- data/ext/clipsruby/dffctpsr.h +49 -0
- data/ext/clipsruby/dffnxbin.c +520 -0
- data/ext/clipsruby/dffnxbin.h +67 -0
- data/ext/clipsruby/dffnxcmp.c +378 -0
- data/ext/clipsruby/dffnxcmp.h +54 -0
- data/ext/clipsruby/dffnxexe.c +241 -0
- data/ext/clipsruby/dffnxexe.h +58 -0
- data/ext/clipsruby/dffnxfun.c +1192 -0
- data/ext/clipsruby/dffnxfun.h +155 -0
- data/ext/clipsruby/dffnxpsr.c +514 -0
- data/ext/clipsruby/dffnxpsr.h +57 -0
- data/ext/clipsruby/dfinsbin.c +509 -0
- data/ext/clipsruby/dfinsbin.h +66 -0
- data/ext/clipsruby/dfinscmp.c +345 -0
- data/ext/clipsruby/dfinscmp.h +48 -0
- data/ext/clipsruby/drive.c +1191 -0
- data/ext/clipsruby/drive.h +65 -0
- data/ext/clipsruby/emathfun.c +1213 -0
- data/ext/clipsruby/emathfun.h +99 -0
- data/ext/clipsruby/engine.c +1568 -0
- data/ext/clipsruby/engine.h +203 -0
- data/ext/clipsruby/entities.h +276 -0
- data/ext/clipsruby/envrnbld.c +514 -0
- data/ext/clipsruby/envrnbld.h +40 -0
- data/ext/clipsruby/envrnmnt.c +257 -0
- data/ext/clipsruby/envrnmnt.h +112 -0
- data/ext/clipsruby/evaluatn.c +1736 -0
- data/ext/clipsruby/evaluatn.h +211 -0
- data/ext/clipsruby/expressn.c +494 -0
- data/ext/clipsruby/expressn.h +154 -0
- data/ext/clipsruby/exprnbin.c +538 -0
- data/ext/clipsruby/exprnbin.h +60 -0
- data/ext/clipsruby/exprnops.c +564 -0
- data/ext/clipsruby/exprnops.h +67 -0
- data/ext/clipsruby/exprnpsr.c +1112 -0
- data/ext/clipsruby/exprnpsr.h +98 -0
- data/ext/clipsruby/extconf.rb +2 -0
- data/ext/clipsruby/extnfunc.c +1015 -0
- data/ext/clipsruby/extnfunc.h +157 -0
- data/ext/clipsruby/factbin.c +447 -0
- data/ext/clipsruby/factbin.h +56 -0
- data/ext/clipsruby/factbld.c +1035 -0
- data/ext/clipsruby/factbld.h +63 -0
- data/ext/clipsruby/factcmp.c +386 -0
- data/ext/clipsruby/factcmp.h +46 -0
- data/ext/clipsruby/factcom.c +759 -0
- data/ext/clipsruby/factcom.h +80 -0
- data/ext/clipsruby/factfile.c +1761 -0
- data/ext/clipsruby/factfile.h +54 -0
- data/ext/clipsruby/factfun.c +682 -0
- data/ext/clipsruby/factfun.h +77 -0
- data/ext/clipsruby/factgen.c +1305 -0
- data/ext/clipsruby/factgen.h +229 -0
- data/ext/clipsruby/facthsh.c +438 -0
- data/ext/clipsruby/facthsh.h +81 -0
- data/ext/clipsruby/factlhs.c +250 -0
- data/ext/clipsruby/factlhs.h +54 -0
- data/ext/clipsruby/factmch.c +905 -0
- data/ext/clipsruby/factmch.h +68 -0
- data/ext/clipsruby/factmngr.c +3373 -0
- data/ext/clipsruby/factmngr.h +325 -0
- data/ext/clipsruby/factprt.c +498 -0
- data/ext/clipsruby/factprt.h +60 -0
- data/ext/clipsruby/factqpsr.c +796 -0
- data/ext/clipsruby/factqpsr.h +61 -0
- data/ext/clipsruby/factqury.c +1267 -0
- data/ext/clipsruby/factqury.h +112 -0
- data/ext/clipsruby/factrete.c +978 -0
- data/ext/clipsruby/factrete.h +70 -0
- data/ext/clipsruby/factrhs.c +667 -0
- data/ext/clipsruby/factrhs.h +55 -0
- data/ext/clipsruby/filecom.c +353 -0
- data/ext/clipsruby/filecom.h +137 -0
- data/ext/clipsruby/filertr.c +481 -0
- data/ext/clipsruby/filertr.h +94 -0
- data/ext/clipsruby/fileutil.c +1020 -0
- data/ext/clipsruby/fileutil.h +50 -0
- data/ext/clipsruby/generate.c +1079 -0
- data/ext/clipsruby/generate.h +57 -0
- data/ext/clipsruby/genrcbin.c +902 -0
- data/ext/clipsruby/genrcbin.h +69 -0
- data/ext/clipsruby/genrccmp.c +640 -0
- data/ext/clipsruby/genrccmp.h +59 -0
- data/ext/clipsruby/genrccom.c +2017 -0
- data/ext/clipsruby/genrccom.h +119 -0
- data/ext/clipsruby/genrcexe.c +737 -0
- data/ext/clipsruby/genrcexe.h +73 -0
- data/ext/clipsruby/genrcfun.c +890 -0
- data/ext/clipsruby/genrcfun.h +185 -0
- data/ext/clipsruby/genrcpsr.c +1618 -0
- data/ext/clipsruby/genrcpsr.h +80 -0
- data/ext/clipsruby/globlbin.c +458 -0
- data/ext/clipsruby/globlbin.h +71 -0
- data/ext/clipsruby/globlbsc.c +361 -0
- data/ext/clipsruby/globlbsc.h +83 -0
- data/ext/clipsruby/globlcmp.c +330 -0
- data/ext/clipsruby/globlcmp.h +52 -0
- data/ext/clipsruby/globlcom.c +289 -0
- data/ext/clipsruby/globlcom.h +63 -0
- data/ext/clipsruby/globldef.c +1087 -0
- data/ext/clipsruby/globldef.h +151 -0
- data/ext/clipsruby/globlpsr.c +530 -0
- data/ext/clipsruby/globlpsr.h +59 -0
- data/ext/clipsruby/immthpsr.c +431 -0
- data/ext/clipsruby/immthpsr.h +55 -0
- data/ext/clipsruby/incrrset.c +530 -0
- data/ext/clipsruby/incrrset.h +73 -0
- data/ext/clipsruby/inherpsr.c +850 -0
- data/ext/clipsruby/inherpsr.h +52 -0
- data/ext/clipsruby/inscom.c +2076 -0
- data/ext/clipsruby/inscom.h +182 -0
- data/ext/clipsruby/insfile.c +1764 -0
- data/ext/clipsruby/insfile.h +96 -0
- data/ext/clipsruby/insfun.c +1451 -0
- data/ext/clipsruby/insfun.h +134 -0
- data/ext/clipsruby/insmngr.c +2550 -0
- data/ext/clipsruby/insmngr.h +125 -0
- data/ext/clipsruby/insmoddp.c +1041 -0
- data/ext/clipsruby/insmoddp.h +91 -0
- data/ext/clipsruby/insmult.c +804 -0
- data/ext/clipsruby/insmult.h +62 -0
- data/ext/clipsruby/inspsr.c +602 -0
- data/ext/clipsruby/inspsr.h +60 -0
- data/ext/clipsruby/insquery.c +1278 -0
- data/ext/clipsruby/insquery.h +115 -0
- data/ext/clipsruby/insqypsr.c +729 -0
- data/ext/clipsruby/insqypsr.h +63 -0
- data/ext/clipsruby/iofun.c +2045 -0
- data/ext/clipsruby/iofun.h +116 -0
- data/ext/clipsruby/lgcldpnd.c +644 -0
- data/ext/clipsruby/lgcldpnd.h +75 -0
- data/ext/clipsruby/main.c +112 -0
- data/ext/clipsruby/match.h +142 -0
- data/ext/clipsruby/memalloc.c +481 -0
- data/ext/clipsruby/memalloc.h +197 -0
- data/ext/clipsruby/miscfun.c +1801 -0
- data/ext/clipsruby/miscfun.h +132 -0
- data/ext/clipsruby/modulbin.c +607 -0
- data/ext/clipsruby/modulbin.h +84 -0
- data/ext/clipsruby/modulbsc.c +347 -0
- data/ext/clipsruby/modulbsc.h +67 -0
- data/ext/clipsruby/modulcmp.c +499 -0
- data/ext/clipsruby/modulcmp.h +54 -0
- data/ext/clipsruby/moduldef.c +817 -0
- data/ext/clipsruby/moduldef.h +271 -0
- data/ext/clipsruby/modulpsr.c +1150 -0
- data/ext/clipsruby/modulpsr.h +69 -0
- data/ext/clipsruby/modulutl.c +1036 -0
- data/ext/clipsruby/modulutl.h +84 -0
- data/ext/clipsruby/msgcom.c +1221 -0
- data/ext/clipsruby/msgcom.h +125 -0
- data/ext/clipsruby/msgfun.c +1076 -0
- data/ext/clipsruby/msgfun.h +118 -0
- data/ext/clipsruby/msgpass.c +1441 -0
- data/ext/clipsruby/msgpass.h +103 -0
- data/ext/clipsruby/msgpsr.c +698 -0
- data/ext/clipsruby/msgpsr.h +73 -0
- data/ext/clipsruby/multifld.c +1404 -0
- data/ext/clipsruby/multifld.h +130 -0
- data/ext/clipsruby/multifun.c +2182 -0
- data/ext/clipsruby/multifun.h +102 -0
- data/ext/clipsruby/network.h +142 -0
- data/ext/clipsruby/objbin.c +1522 -0
- data/ext/clipsruby/objbin.h +79 -0
- data/ext/clipsruby/objcmp.c +1507 -0
- data/ext/clipsruby/objcmp.h +71 -0
- data/ext/clipsruby/object.h +260 -0
- data/ext/clipsruby/objrtbin.c +701 -0
- data/ext/clipsruby/objrtbin.h +79 -0
- data/ext/clipsruby/objrtbld.c +2393 -0
- data/ext/clipsruby/objrtbld.h +66 -0
- data/ext/clipsruby/objrtcmp.c +734 -0
- data/ext/clipsruby/objrtcmp.h +66 -0
- data/ext/clipsruby/objrtfnx.c +1330 -0
- data/ext/clipsruby/objrtfnx.h +222 -0
- data/ext/clipsruby/objrtgen.c +736 -0
- data/ext/clipsruby/objrtgen.h +63 -0
- data/ext/clipsruby/objrtmch.c +1524 -0
- data/ext/clipsruby/objrtmch.h +160 -0
- data/ext/clipsruby/parsefun.c +415 -0
- data/ext/clipsruby/parsefun.h +67 -0
- data/ext/clipsruby/pattern.c +1265 -0
- data/ext/clipsruby/pattern.h +163 -0
- data/ext/clipsruby/pprint.c +328 -0
- data/ext/clipsruby/pprint.h +79 -0
- data/ext/clipsruby/prccode.c +1478 -0
- data/ext/clipsruby/prccode.h +145 -0
- data/ext/clipsruby/prcdrfun.c +640 -0
- data/ext/clipsruby/prcdrfun.h +95 -0
- data/ext/clipsruby/prcdrpsr.c +1068 -0
- data/ext/clipsruby/prcdrpsr.h +79 -0
- data/ext/clipsruby/prdctfun.c +869 -0
- data/ext/clipsruby/prdctfun.h +77 -0
- data/ext/clipsruby/prntutil.c +878 -0
- data/ext/clipsruby/prntutil.h +125 -0
- data/ext/clipsruby/proflfun.c +827 -0
- data/ext/clipsruby/proflfun.h +118 -0
- data/ext/clipsruby/reorder.c +2082 -0
- data/ext/clipsruby/reorder.h +172 -0
- data/ext/clipsruby/reteutil.c +1732 -0
- data/ext/clipsruby/reteutil.h +111 -0
- data/ext/clipsruby/retract.c +710 -0
- data/ext/clipsruby/retract.h +74 -0
- data/ext/clipsruby/router.c +737 -0
- data/ext/clipsruby/router.h +147 -0
- data/ext/clipsruby/rulebin.c +1136 -0
- data/ext/clipsruby/rulebin.h +153 -0
- data/ext/clipsruby/rulebld.c +1328 -0
- data/ext/clipsruby/rulebld.h +62 -0
- data/ext/clipsruby/rulebsc.c +517 -0
- data/ext/clipsruby/rulebsc.h +91 -0
- data/ext/clipsruby/rulecmp.c +733 -0
- data/ext/clipsruby/rulecmp.h +63 -0
- data/ext/clipsruby/rulecom.c +1583 -0
- data/ext/clipsruby/rulecom.h +116 -0
- data/ext/clipsruby/rulecstr.c +892 -0
- data/ext/clipsruby/rulecstr.h +53 -0
- data/ext/clipsruby/ruledef.c +559 -0
- data/ext/clipsruby/ruledef.h +179 -0
- data/ext/clipsruby/ruledlt.c +599 -0
- data/ext/clipsruby/ruledlt.h +58 -0
- data/ext/clipsruby/rulelhs.c +1216 -0
- data/ext/clipsruby/rulelhs.h +52 -0
- data/ext/clipsruby/rulepsr.c +1073 -0
- data/ext/clipsruby/rulepsr.h +61 -0
- data/ext/clipsruby/scanner.c +856 -0
- data/ext/clipsruby/scanner.h +112 -0
- data/ext/clipsruby/setup.h +488 -0
- data/ext/clipsruby/sortfun.c +433 -0
- data/ext/clipsruby/sortfun.h +55 -0
- data/ext/clipsruby/strngfun.c +1173 -0
- data/ext/clipsruby/strngfun.h +96 -0
- data/ext/clipsruby/strngrtr.c +523 -0
- data/ext/clipsruby/strngrtr.h +97 -0
- data/ext/clipsruby/symblbin.c +648 -0
- data/ext/clipsruby/symblbin.h +64 -0
- data/ext/clipsruby/symblcmp.c +893 -0
- data/ext/clipsruby/symblcmp.h +61 -0
- data/ext/clipsruby/symbol.c +1961 -0
- data/ext/clipsruby/symbol.h +243 -0
- data/ext/clipsruby/sysdep.c +894 -0
- data/ext/clipsruby/sysdep.h +164 -0
- data/ext/clipsruby/textpro.c +1388 -0
- data/ext/clipsruby/textpro.h +77 -0
- data/ext/clipsruby/tmpltbin.c +609 -0
- data/ext/clipsruby/tmpltbin.h +108 -0
- data/ext/clipsruby/tmpltbsc.c +327 -0
- data/ext/clipsruby/tmpltbsc.h +87 -0
- data/ext/clipsruby/tmpltcmp.c +450 -0
- data/ext/clipsruby/tmpltcmp.h +57 -0
- data/ext/clipsruby/tmpltdef.c +584 -0
- data/ext/clipsruby/tmpltdef.h +155 -0
- data/ext/clipsruby/tmpltfun.c +2477 -0
- data/ext/clipsruby/tmpltfun.h +122 -0
- data/ext/clipsruby/tmpltlhs.c +379 -0
- data/ext/clipsruby/tmpltlhs.h +50 -0
- data/ext/clipsruby/tmpltpsr.c +819 -0
- data/ext/clipsruby/tmpltpsr.h +59 -0
- data/ext/clipsruby/tmpltrhs.c +595 -0
- data/ext/clipsruby/tmpltrhs.h +55 -0
- data/ext/clipsruby/tmpltutl.c +637 -0
- data/ext/clipsruby/tmpltutl.h +82 -0
- data/ext/clipsruby/userdata.c +156 -0
- data/ext/clipsruby/userdata.h +72 -0
- data/ext/clipsruby/userfunctions.c +70 -0
- data/ext/clipsruby/usrsetup.h +7 -0
- data/ext/clipsruby/utility.c +1594 -0
- data/ext/clipsruby/utility.h +250 -0
- data/ext/clipsruby/watch.c +865 -0
- data/ext/clipsruby/watch.h +124 -0
- data/lib/clipsruby.rb +1 -0
- metadata +388 -0
@@ -0,0 +1,1376 @@
|
|
1
|
+
/*******************************************************/
|
2
|
+
/* "C" Language Integrated Production System */
|
3
|
+
/* */
|
4
|
+
/* CLIPS Version 6.41 12/04/22 */
|
5
|
+
/* */
|
6
|
+
/* CLASS EXAMINATION MODULE */
|
7
|
+
/*******************************************************/
|
8
|
+
|
9
|
+
/**************************************************************/
|
10
|
+
/* Purpose: Class browsing and examination commands */
|
11
|
+
/* */
|
12
|
+
/* Principal Programmer(s): */
|
13
|
+
/* Brian L. Dantes */
|
14
|
+
/* */
|
15
|
+
/* Contributing Programmer(s): */
|
16
|
+
/* */
|
17
|
+
/* Revision History: */
|
18
|
+
/* */
|
19
|
+
/* 6.23: Correction for FalseSymbol/TrueSymbol. DR0859 */
|
20
|
+
/* */
|
21
|
+
/* Modified the slot-writablep function to return */
|
22
|
+
/* FALSE for slots having initialize-only access. */
|
23
|
+
/* DR0860 */
|
24
|
+
/* */
|
25
|
+
/* 6.24: Added allowed-classes slot facet. */
|
26
|
+
/* */
|
27
|
+
/* Converted INSTANCE_PATTERN_MATCHING to */
|
28
|
+
/* DEFRULE_CONSTRUCT. */
|
29
|
+
/* */
|
30
|
+
/* Renamed BOOLEAN macro type to intBool. */
|
31
|
+
/* */
|
32
|
+
/* The slot-default-value function crashes when no */
|
33
|
+
/* default exists for a slot (the ?NONE value was */
|
34
|
+
/* specified). DR0870 */
|
35
|
+
/* */
|
36
|
+
/* 6.30: Used %zd for printing size_t arguments. */
|
37
|
+
/* */
|
38
|
+
/* Added EnvSlotDefaultP function. */
|
39
|
+
/* */
|
40
|
+
/* Borland C (IBM_TBC) and Metrowerks CodeWarrior */
|
41
|
+
/* (MAC_MCW, IBM_MCW) are no longer supported. */
|
42
|
+
/* */
|
43
|
+
/* Used gensprintf and genstrcat instead of */
|
44
|
+
/* sprintf and strcat. */
|
45
|
+
/* */
|
46
|
+
/* Added const qualifiers to remove C++ */
|
47
|
+
/* deprecation warnings. */
|
48
|
+
/* */
|
49
|
+
/* Converted API macros to function calls. */
|
50
|
+
/* */
|
51
|
+
/* 6.40: Added Env prefix to GetEvaluationError and */
|
52
|
+
/* SetEvaluationError functions. */
|
53
|
+
/* */
|
54
|
+
/* Pragma once and other inclusion changes. */
|
55
|
+
/* */
|
56
|
+
/* Added support for booleans with <stdbool.h>. */
|
57
|
+
/* */
|
58
|
+
/* Removed use of void pointers for specific */
|
59
|
+
/* data structures. */
|
60
|
+
/* */
|
61
|
+
/* ALLOW_ENVIRONMENT_GLOBALS no longer supported. */
|
62
|
+
/* */
|
63
|
+
/* UDF redesign. */
|
64
|
+
/* */
|
65
|
+
/* 6.41: Used gensnprintf in place of gensprintf and. */
|
66
|
+
/* sprintf. */
|
67
|
+
/* */
|
68
|
+
/**************************************************************/
|
69
|
+
|
70
|
+
/* =========================================
|
71
|
+
*****************************************
|
72
|
+
EXTERNAL DEFINITIONS
|
73
|
+
=========================================
|
74
|
+
***************************************** */
|
75
|
+
#include "setup.h"
|
76
|
+
|
77
|
+
#if OBJECT_SYSTEM
|
78
|
+
|
79
|
+
#include <string.h>
|
80
|
+
|
81
|
+
#include "argacces.h"
|
82
|
+
#include "classcom.h"
|
83
|
+
#include "classfun.h"
|
84
|
+
#include "classini.h"
|
85
|
+
#include "envrnmnt.h"
|
86
|
+
#include "insfun.h"
|
87
|
+
#include "memalloc.h"
|
88
|
+
#include "msgcom.h"
|
89
|
+
#include "msgfun.h"
|
90
|
+
#include "prntutil.h"
|
91
|
+
#include "router.h"
|
92
|
+
#include "strngrtr.h"
|
93
|
+
#include "sysdep.h"
|
94
|
+
|
95
|
+
#include "classexm.h"
|
96
|
+
|
97
|
+
/***************************************/
|
98
|
+
/* LOCAL INTERNAL FUNCTION DEFINITIONS */
|
99
|
+
/***************************************/
|
100
|
+
|
101
|
+
static bool CheckTwoClasses(UDFContext *,const char *,Defclass **,Defclass **);
|
102
|
+
static SlotDescriptor *CheckSlotExists(UDFContext *,const char *,Defclass **,bool,bool);
|
103
|
+
static SlotDescriptor *LookupSlot(Environment *,Defclass *,const char *,bool);
|
104
|
+
|
105
|
+
#if DEBUGGING_FUNCTIONS
|
106
|
+
static Defclass *CheckClass(Environment *,const char *,const char *);
|
107
|
+
static const char *GetClassNameArgument(UDFContext *);
|
108
|
+
static void PrintClassBrowse(Environment *,const char *,Defclass *,unsigned long);
|
109
|
+
static void DisplaySeparator(Environment *,const char *,char *,int,int);
|
110
|
+
static void DisplaySlotBasicInfo(Environment *,const char *,const char *,const char *,
|
111
|
+
char *,Defclass *);
|
112
|
+
static bool PrintSlotSources(Environment *,const char *,CLIPSLexeme *,PACKED_CLASS_LINKS *,
|
113
|
+
unsigned long,bool);
|
114
|
+
static void DisplaySlotConstraintInfo(Environment *,const char *,const char *,char *,unsigned,Defclass *);
|
115
|
+
static const char *ConstraintCode(CONSTRAINT_RECORD *,unsigned,unsigned);
|
116
|
+
#endif
|
117
|
+
|
118
|
+
/* =========================================
|
119
|
+
*****************************************
|
120
|
+
EXTERNALLY VISIBLE FUNCTIONS
|
121
|
+
=========================================
|
122
|
+
***************************************** */
|
123
|
+
|
124
|
+
#if DEBUGGING_FUNCTIONS
|
125
|
+
|
126
|
+
/****************************************************************
|
127
|
+
NAME : BrowseClassesCommand
|
128
|
+
DESCRIPTION : Displays a "graph" of the class hierarchy
|
129
|
+
INPUTS : None
|
130
|
+
RETURNS : Nothing useful
|
131
|
+
SIDE EFFECTS : None
|
132
|
+
NOTES : Syntax : (browse-classes [<class>])
|
133
|
+
****************************************************************/
|
134
|
+
void BrowseClassesCommand(
|
135
|
+
Environment *theEnv,
|
136
|
+
UDFContext *context,
|
137
|
+
UDFValue *returnValue)
|
138
|
+
{
|
139
|
+
Defclass *cls;
|
140
|
+
|
141
|
+
if (UDFArgumentCount(context) == 0)
|
142
|
+
/* ================================================
|
143
|
+
Find the OBJECT root class (has no superclasses)
|
144
|
+
================================================ */
|
145
|
+
cls = LookupDefclassByMdlOrScope(theEnv,OBJECT_TYPE_NAME);
|
146
|
+
else
|
147
|
+
{
|
148
|
+
UDFValue theArg;
|
149
|
+
|
150
|
+
if (! UDFFirstArgument(context,SYMBOL_BIT,&theArg))
|
151
|
+
return;
|
152
|
+
cls = LookupDefclassByMdlOrScope(theEnv,theArg.lexemeValue->contents);
|
153
|
+
if (cls == NULL)
|
154
|
+
{
|
155
|
+
ClassExistError(theEnv,"browse-classes",theArg.lexemeValue->contents);
|
156
|
+
return;
|
157
|
+
}
|
158
|
+
}
|
159
|
+
BrowseClasses(cls,STDOUT);
|
160
|
+
}
|
161
|
+
|
162
|
+
/****************************************************************
|
163
|
+
NAME : BrowseClasses
|
164
|
+
DESCRIPTION : Displays a "graph" of the class hierarchy
|
165
|
+
INPUTS : 1) The logical name of the output
|
166
|
+
2) Class pointer
|
167
|
+
RETURNS : Nothing useful
|
168
|
+
SIDE EFFECTS : None
|
169
|
+
NOTES : None
|
170
|
+
****************************************************************/
|
171
|
+
void BrowseClasses(
|
172
|
+
Defclass *theDefclass,
|
173
|
+
const char *logicalName)
|
174
|
+
{
|
175
|
+
Environment *theEnv = theDefclass->header.env;
|
176
|
+
|
177
|
+
PrintClassBrowse(theEnv,logicalName,theDefclass,0);
|
178
|
+
}
|
179
|
+
|
180
|
+
/****************************************************************
|
181
|
+
NAME : DescribeClassCommand
|
182
|
+
DESCRIPTION : Displays direct superclasses and
|
183
|
+
subclasses and the entire precedence
|
184
|
+
list for a class
|
185
|
+
INPUTS : None
|
186
|
+
RETURNS : Nothing useful
|
187
|
+
SIDE EFFECTS : None
|
188
|
+
NOTES : Syntax : (describe-class <class-name>)
|
189
|
+
****************************************************************/
|
190
|
+
void DescribeClassCommand(
|
191
|
+
Environment *theEnv,
|
192
|
+
UDFContext *context,
|
193
|
+
UDFValue *returnValue)
|
194
|
+
{
|
195
|
+
const char *className;
|
196
|
+
Defclass *theDefclass;
|
197
|
+
|
198
|
+
className = GetClassNameArgument(context);
|
199
|
+
|
200
|
+
if (className == NULL)
|
201
|
+
{ return; }
|
202
|
+
|
203
|
+
theDefclass = CheckClass(theEnv,"describe-class",className);
|
204
|
+
|
205
|
+
if (theDefclass == NULL)
|
206
|
+
{ return; }
|
207
|
+
|
208
|
+
DescribeClass(theDefclass,STDOUT);
|
209
|
+
}
|
210
|
+
|
211
|
+
/******************************************************
|
212
|
+
NAME : DescribeClass
|
213
|
+
DESCRIPTION : Displays direct superclasses and
|
214
|
+
subclasses and the entire precedence
|
215
|
+
list for a class
|
216
|
+
INPUTS : 1) The logical name of the output
|
217
|
+
2) Class pointer
|
218
|
+
RETURNS : Nothing useful
|
219
|
+
SIDE EFFECTS : None
|
220
|
+
NOTES : None
|
221
|
+
******************************************************/
|
222
|
+
void DescribeClass(
|
223
|
+
Defclass *theDefclass,
|
224
|
+
const char *logicalName)
|
225
|
+
{
|
226
|
+
char buf[83],
|
227
|
+
slotNamePrintFormat[12],
|
228
|
+
overrideMessagePrintFormat[12];
|
229
|
+
bool messageBanner;
|
230
|
+
unsigned long i;
|
231
|
+
size_t slotNameLength, maxSlotNameLength;
|
232
|
+
size_t overrideMessageLength, maxOverrideMessageLength;
|
233
|
+
Environment *theEnv = theDefclass->header.env;
|
234
|
+
|
235
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'=');
|
236
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'*');
|
237
|
+
if (theDefclass->abstract)
|
238
|
+
WriteString(theEnv,logicalName,"Abstract: direct instances of this class cannot be created.\n\n");
|
239
|
+
else
|
240
|
+
{
|
241
|
+
WriteString(theEnv,logicalName,"Concrete: direct instances of this class can be created.\n");
|
242
|
+
#if DEFRULE_CONSTRUCT
|
243
|
+
if (theDefclass->reactive)
|
244
|
+
WriteString(theEnv,logicalName,"Reactive: direct instances of this class can match defrule patterns.\n\n");
|
245
|
+
else
|
246
|
+
WriteString(theEnv,logicalName,"Non-reactive: direct instances of this class cannot match defrule patterns.\n\n");
|
247
|
+
#else
|
248
|
+
WriteString(theEnv,logicalName,"\n");
|
249
|
+
#endif
|
250
|
+
}
|
251
|
+
PrintPackedClassLinks(theEnv,logicalName,"Direct Superclasses:",&theDefclass->directSuperclasses);
|
252
|
+
PrintPackedClassLinks(theEnv,logicalName,"Inheritance Precedence:",&theDefclass->allSuperclasses);
|
253
|
+
PrintPackedClassLinks(theEnv,logicalName,"Direct Subclasses:",&theDefclass->directSubclasses);
|
254
|
+
if (theDefclass->instanceTemplate != NULL)
|
255
|
+
{
|
256
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'-');
|
257
|
+
maxSlotNameLength = 5;
|
258
|
+
maxOverrideMessageLength = 8;
|
259
|
+
for (i = 0 ; i < theDefclass->instanceSlotCount ; i++)
|
260
|
+
{
|
261
|
+
slotNameLength = strlen(theDefclass->instanceTemplate[i]->slotName->name->contents);
|
262
|
+
if (slotNameLength > maxSlotNameLength)
|
263
|
+
maxSlotNameLength = slotNameLength;
|
264
|
+
if (theDefclass->instanceTemplate[i]->noWrite == 0)
|
265
|
+
{
|
266
|
+
overrideMessageLength =
|
267
|
+
strlen(theDefclass->instanceTemplate[i]->overrideMessage->contents);
|
268
|
+
if (overrideMessageLength > maxOverrideMessageLength)
|
269
|
+
maxOverrideMessageLength = overrideMessageLength;
|
270
|
+
}
|
271
|
+
}
|
272
|
+
if (maxSlotNameLength > 16)
|
273
|
+
maxSlotNameLength = 16;
|
274
|
+
if (maxOverrideMessageLength > 12)
|
275
|
+
maxOverrideMessageLength = 12;
|
276
|
+
|
277
|
+
gensnprintf(slotNamePrintFormat,sizeof(slotNamePrintFormat),"%%-%zd.%zds : ",maxSlotNameLength,maxSlotNameLength);
|
278
|
+
gensnprintf(overrideMessagePrintFormat,sizeof(overrideMessagePrintFormat),"%%-%zd.%zds ",maxOverrideMessageLength,
|
279
|
+
maxOverrideMessageLength);
|
280
|
+
|
281
|
+
DisplaySlotBasicInfo(theEnv,logicalName,slotNamePrintFormat,overrideMessagePrintFormat,buf,theDefclass);
|
282
|
+
WriteString(theEnv,logicalName,"\nConstraint information for slots:\n\n");
|
283
|
+
DisplaySlotConstraintInfo(theEnv,logicalName,slotNamePrintFormat,buf,82,theDefclass);
|
284
|
+
}
|
285
|
+
if (theDefclass->handlerCount > 0)
|
286
|
+
messageBanner = true;
|
287
|
+
else
|
288
|
+
{
|
289
|
+
messageBanner = false;
|
290
|
+
for (i = 1 ; i < theDefclass->allSuperclasses.classCount ; i++)
|
291
|
+
if (theDefclass->allSuperclasses.classArray[i]->handlerCount > 0)
|
292
|
+
{
|
293
|
+
messageBanner = true;
|
294
|
+
break;
|
295
|
+
}
|
296
|
+
}
|
297
|
+
if (messageBanner)
|
298
|
+
{
|
299
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'-');
|
300
|
+
WriteString(theEnv,logicalName,"Recognized message-handlers:\n");
|
301
|
+
DisplayHandlersInLinks(theEnv,logicalName,&theDefclass->allSuperclasses,0);
|
302
|
+
}
|
303
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'*');
|
304
|
+
DisplaySeparator(theEnv,logicalName,buf,82,'=');
|
305
|
+
}
|
306
|
+
|
307
|
+
#endif /* DEBUGGING_FUNCTIONS */
|
308
|
+
|
309
|
+
/**********************************************************
|
310
|
+
NAME : GetCreateAccessorString
|
311
|
+
DESCRIPTION : Gets a string describing which
|
312
|
+
accessors are implicitly created
|
313
|
+
for a slot: R, W, RW or NIL
|
314
|
+
INPUTS : The slot descriptor
|
315
|
+
RETURNS : The string description
|
316
|
+
SIDE EFFECTS : None
|
317
|
+
NOTES : Used by (describe-class) and (slot-facets)
|
318
|
+
**********************************************************/
|
319
|
+
const char *GetCreateAccessorString(
|
320
|
+
SlotDescriptor *sd)
|
321
|
+
{
|
322
|
+
if (sd->createReadAccessor && sd->createWriteAccessor)
|
323
|
+
return("RW");
|
324
|
+
|
325
|
+
if ((sd->createReadAccessor == 0) && (sd->createWriteAccessor == 0))
|
326
|
+
return("NIL");
|
327
|
+
else
|
328
|
+
{
|
329
|
+
if (sd->createReadAccessor) return "R";
|
330
|
+
else return "W";
|
331
|
+
}
|
332
|
+
}
|
333
|
+
|
334
|
+
/************************************************************
|
335
|
+
NAME : GetDefclassModuleCommand
|
336
|
+
DESCRIPTION : Determines to which module a class belongs
|
337
|
+
INPUTS : None
|
338
|
+
RETURNS : The symbolic name of the module
|
339
|
+
SIDE EFFECTS : None
|
340
|
+
NOTES : H/L Syntax: (defclass-module <class-name>)
|
341
|
+
************************************************************/
|
342
|
+
void GetDefclassModuleCommand(
|
343
|
+
Environment *theEnv,
|
344
|
+
UDFContext *context,
|
345
|
+
UDFValue *returnValue)
|
346
|
+
{
|
347
|
+
returnValue->value = GetConstructModuleCommand(context,"defclass-module",DefclassData(theEnv)->DefclassConstruct);
|
348
|
+
}
|
349
|
+
|
350
|
+
/*********************************************************************
|
351
|
+
NAME : SuperclassPCommand
|
352
|
+
DESCRIPTION : Determines if a class is a superclass of another
|
353
|
+
INPUTS : None
|
354
|
+
RETURNS : True if class-1 is a superclass of class-2
|
355
|
+
SIDE EFFECTS : None
|
356
|
+
NOTES : H/L Syntax : (superclassp <class-1> <class-2>)
|
357
|
+
*********************************************************************/
|
358
|
+
void SuperclassPCommand(
|
359
|
+
Environment *theEnv,
|
360
|
+
UDFContext *context,
|
361
|
+
UDFValue *returnValue)
|
362
|
+
{
|
363
|
+
Defclass *c1, *c2;
|
364
|
+
|
365
|
+
if (CheckTwoClasses(context,"superclassp",&c1,&c2) == false)
|
366
|
+
{
|
367
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
368
|
+
return;
|
369
|
+
}
|
370
|
+
|
371
|
+
returnValue->lexemeValue = CreateBoolean(theEnv,SuperclassP(c1,c2));
|
372
|
+
}
|
373
|
+
|
374
|
+
/***************************************************
|
375
|
+
NAME : SuperclassP
|
376
|
+
DESCRIPTION : Determines if the first class is
|
377
|
+
a superclass of the other
|
378
|
+
INPUTS : 1) First class
|
379
|
+
2) Second class
|
380
|
+
RETURNS : True if first class is a
|
381
|
+
superclass of the first,
|
382
|
+
false otherwise
|
383
|
+
SIDE EFFECTS : None
|
384
|
+
NOTES : None
|
385
|
+
***************************************************/
|
386
|
+
bool SuperclassP(
|
387
|
+
Defclass *firstClass,
|
388
|
+
Defclass *secondClass)
|
389
|
+
{
|
390
|
+
return HasSuperclass(secondClass,firstClass);
|
391
|
+
}
|
392
|
+
|
393
|
+
/*********************************************************************
|
394
|
+
NAME : SubclassPCommand
|
395
|
+
DESCRIPTION : Determines if a class is a subclass of another
|
396
|
+
INPUTS : None
|
397
|
+
RETURNS : True if class-1 is a subclass of class-2
|
398
|
+
SIDE EFFECTS : None
|
399
|
+
NOTES : H/L Syntax : (subclassp <class-1> <class-2>)
|
400
|
+
*********************************************************************/
|
401
|
+
void SubclassPCommand(
|
402
|
+
Environment *theEnv,
|
403
|
+
UDFContext *context,
|
404
|
+
UDFValue *returnValue)
|
405
|
+
{
|
406
|
+
Defclass *c1, *c2;
|
407
|
+
|
408
|
+
if (CheckTwoClasses(context,"subclassp",&c1,&c2) == false)
|
409
|
+
{
|
410
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
411
|
+
return;
|
412
|
+
}
|
413
|
+
|
414
|
+
returnValue->lexemeValue = CreateBoolean(theEnv,SubclassP(c1,c2));
|
415
|
+
}
|
416
|
+
|
417
|
+
/***************************************************
|
418
|
+
NAME : SubclassP
|
419
|
+
DESCRIPTION : Determines if the first class is
|
420
|
+
a subclass of the other
|
421
|
+
INPUTS : 1) First class
|
422
|
+
2) Second class
|
423
|
+
RETURNS : True if first class is a
|
424
|
+
subclass of the first,
|
425
|
+
false otherwise
|
426
|
+
SIDE EFFECTS : None
|
427
|
+
NOTES : None
|
428
|
+
***************************************************/
|
429
|
+
bool SubclassP(
|
430
|
+
Defclass *firstClass,
|
431
|
+
Defclass *secondClass)
|
432
|
+
{
|
433
|
+
return HasSuperclass(firstClass,secondClass);
|
434
|
+
}
|
435
|
+
|
436
|
+
/*********************************************************************
|
437
|
+
NAME : SlotExistPCommand
|
438
|
+
DESCRIPTION : Determines if a slot is present in a class
|
439
|
+
INPUTS : None
|
440
|
+
RETURNS : True if the slot exists, false otherwise
|
441
|
+
SIDE EFFECTS : None
|
442
|
+
NOTES : H/L Syntax : (slot-existp <class> <slot> [inherit])
|
443
|
+
*********************************************************************/
|
444
|
+
void SlotExistPCommand(
|
445
|
+
Environment *theEnv,
|
446
|
+
UDFContext *context,
|
447
|
+
UDFValue *returnValue)
|
448
|
+
{
|
449
|
+
Defclass *cls;
|
450
|
+
SlotDescriptor *sd;
|
451
|
+
bool inheritFlag = false;
|
452
|
+
UDFValue theArg;
|
453
|
+
|
454
|
+
sd = CheckSlotExists(context,"slot-existp",&cls,false,true);
|
455
|
+
if (sd == NULL)
|
456
|
+
{
|
457
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
458
|
+
return;
|
459
|
+
}
|
460
|
+
|
461
|
+
if (UDFHasNextArgument(context))
|
462
|
+
{
|
463
|
+
if (! UDFNextArgument(context,SYMBOL_BIT,&theArg))
|
464
|
+
{ return; }
|
465
|
+
|
466
|
+
if (strcmp(theArg.lexemeValue->contents,"inherit") != 0)
|
467
|
+
{
|
468
|
+
UDFInvalidArgumentMessage(context,"keyword \"inherit\"");
|
469
|
+
SetEvaluationError(theEnv,true);
|
470
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
471
|
+
return;
|
472
|
+
}
|
473
|
+
inheritFlag = true;
|
474
|
+
}
|
475
|
+
|
476
|
+
returnValue->lexemeValue = CreateBoolean(theEnv,((sd->cls == cls) ? true : inheritFlag));
|
477
|
+
}
|
478
|
+
|
479
|
+
/***************************************************
|
480
|
+
NAME : SlotExistP
|
481
|
+
DESCRIPTION : Determines if a slot exists
|
482
|
+
INPUTS : 1) The class
|
483
|
+
2) The slot name
|
484
|
+
3) A flag indicating if the slot
|
485
|
+
can be inherited or not
|
486
|
+
RETURNS : True if slot exists,
|
487
|
+
false otherwise
|
488
|
+
SIDE EFFECTS : None
|
489
|
+
NOTES : None
|
490
|
+
***************************************************/
|
491
|
+
bool SlotExistP(
|
492
|
+
Defclass *theDefclass,
|
493
|
+
const char *slotName,
|
494
|
+
bool inheritFlag)
|
495
|
+
{
|
496
|
+
Environment *theEnv = theDefclass->header.env;
|
497
|
+
|
498
|
+
return (LookupSlot(theEnv,theDefclass,slotName,inheritFlag) != NULL)
|
499
|
+
? true : false;
|
500
|
+
}
|
501
|
+
|
502
|
+
/************************************************************************************
|
503
|
+
NAME : MessageHandlerExistPCommand
|
504
|
+
DESCRIPTION : Determines if a message-handler is present in a class
|
505
|
+
INPUTS : None
|
506
|
+
RETURNS : True if the message header is present, false otherwise
|
507
|
+
SIDE EFFECTS : None
|
508
|
+
NOTES : H/L Syntax : (message-handler-existp <class> <hnd> [<type>])
|
509
|
+
************************************************************************************/
|
510
|
+
void MessageHandlerExistPCommand(
|
511
|
+
Environment *theEnv,
|
512
|
+
UDFContext *context,
|
513
|
+
UDFValue *returnValue)
|
514
|
+
{
|
515
|
+
Defclass *cls;
|
516
|
+
CLIPSLexeme *mname;
|
517
|
+
UDFValue theArg;
|
518
|
+
unsigned mtype = MPRIMARY;
|
519
|
+
|
520
|
+
if (! UDFFirstArgument(context,SYMBOL_BIT,&theArg))
|
521
|
+
{ return; }
|
522
|
+
cls = LookupDefclassByMdlOrScope(theEnv,theArg.lexemeValue->contents);
|
523
|
+
if (cls == NULL)
|
524
|
+
{
|
525
|
+
ClassExistError(theEnv,"message-handler-existp",theArg.lexemeValue->contents);
|
526
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
527
|
+
return;
|
528
|
+
}
|
529
|
+
|
530
|
+
if (! UDFNextArgument(context,SYMBOL_BIT,&theArg))
|
531
|
+
{ return; }
|
532
|
+
|
533
|
+
mname = theArg.lexemeValue;
|
534
|
+
if (UDFHasNextArgument(context))
|
535
|
+
{
|
536
|
+
if (! UDFNextArgument(context,SYMBOL_BIT,&theArg))
|
537
|
+
{ return; }
|
538
|
+
|
539
|
+
mtype = HandlerType(theEnv,"message-handler-existp",true,theArg.lexemeValue->contents);
|
540
|
+
if (mtype == MERROR)
|
541
|
+
{
|
542
|
+
SetEvaluationError(theEnv,true);
|
543
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
544
|
+
return;
|
545
|
+
}
|
546
|
+
}
|
547
|
+
|
548
|
+
if (FindHandlerByAddress(cls,mname,mtype) != NULL)
|
549
|
+
{ returnValue->lexemeValue = TrueSymbol(theEnv); }
|
550
|
+
else
|
551
|
+
{ returnValue->lexemeValue = FalseSymbol(theEnv); }
|
552
|
+
}
|
553
|
+
|
554
|
+
/**********************************************************************
|
555
|
+
NAME : SlotWritablePCommand
|
556
|
+
DESCRIPTION : Determines if an existing slot can be written to
|
557
|
+
INPUTS : None
|
558
|
+
RETURNS : True if the slot is writable, false otherwise
|
559
|
+
SIDE EFFECTS : None
|
560
|
+
NOTES : H/L Syntax : (slot-writablep <class> <slot>)
|
561
|
+
**********************************************************************/
|
562
|
+
void SlotWritablePCommand(
|
563
|
+
Environment *theEnv,
|
564
|
+
UDFContext *context,
|
565
|
+
UDFValue *returnValue)
|
566
|
+
{
|
567
|
+
Defclass *theDefclass;
|
568
|
+
SlotDescriptor *sd;
|
569
|
+
|
570
|
+
sd = CheckSlotExists(context,"slot-writablep",&theDefclass,true,true);
|
571
|
+
if (sd == NULL)
|
572
|
+
{ returnValue->lexemeValue = FalseSymbol(theEnv); }
|
573
|
+
else
|
574
|
+
{ returnValue->lexemeValue = CreateBoolean(theEnv,(sd->noWrite || sd->initializeOnly) ? false : true); }
|
575
|
+
}
|
576
|
+
|
577
|
+
/***************************************************
|
578
|
+
NAME : SlotWritableP
|
579
|
+
DESCRIPTION : Determines if a slot is writable
|
580
|
+
INPUTS : 1) The class
|
581
|
+
2) The slot name
|
582
|
+
RETURNS : True if slot is writable,
|
583
|
+
false otherwise
|
584
|
+
SIDE EFFECTS : None
|
585
|
+
NOTES : None
|
586
|
+
***************************************************/
|
587
|
+
bool SlotWritableP(
|
588
|
+
Defclass *theDefclass,
|
589
|
+
const char *slotName)
|
590
|
+
{
|
591
|
+
SlotDescriptor *sd;
|
592
|
+
Environment *theEnv = theDefclass->header.env;
|
593
|
+
|
594
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,true)) == NULL)
|
595
|
+
return false;
|
596
|
+
return((sd->noWrite || sd->initializeOnly) ? false : true);
|
597
|
+
}
|
598
|
+
|
599
|
+
/**********************************************************************
|
600
|
+
NAME : SlotInitablePCommand
|
601
|
+
DESCRIPTION : Determines if an existing slot can be initialized
|
602
|
+
via an init message-handler or slot-override
|
603
|
+
INPUTS : None
|
604
|
+
RETURNS : True if the slot is writable, false otherwise
|
605
|
+
SIDE EFFECTS : None
|
606
|
+
NOTES : H/L Syntax : (slot-initablep <class> <slot>)
|
607
|
+
**********************************************************************/
|
608
|
+
void SlotInitablePCommand(
|
609
|
+
Environment *theEnv,
|
610
|
+
UDFContext *context,
|
611
|
+
UDFValue *returnValue)
|
612
|
+
{
|
613
|
+
Defclass *theDefclass;
|
614
|
+
SlotDescriptor *sd;
|
615
|
+
|
616
|
+
sd = CheckSlotExists(context,"slot-initablep",&theDefclass,true,true);
|
617
|
+
if (sd == NULL)
|
618
|
+
{ returnValue->lexemeValue = FalseSymbol(theEnv); }
|
619
|
+
else
|
620
|
+
{ returnValue->lexemeValue = CreateBoolean(theEnv,(sd->noWrite && (sd->initializeOnly == 0)) ? false : true); }
|
621
|
+
}
|
622
|
+
|
623
|
+
/***************************************************
|
624
|
+
NAME : SlotInitableP
|
625
|
+
DESCRIPTION : Determines if a slot is initable
|
626
|
+
INPUTS : 1) The class
|
627
|
+
2) The slot name
|
628
|
+
RETURNS : True if slot is initable,
|
629
|
+
false otherwise
|
630
|
+
SIDE EFFECTS : None
|
631
|
+
NOTES : None
|
632
|
+
***************************************************/
|
633
|
+
bool SlotInitableP(
|
634
|
+
Defclass *theDefclass,
|
635
|
+
const char *slotName)
|
636
|
+
{
|
637
|
+
SlotDescriptor *sd;
|
638
|
+
Environment *theEnv = theDefclass->header.env;
|
639
|
+
|
640
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,true)) == NULL)
|
641
|
+
return false;
|
642
|
+
return((sd->noWrite && (sd->initializeOnly == 0)) ? false : true);
|
643
|
+
}
|
644
|
+
|
645
|
+
/**********************************************************************
|
646
|
+
NAME : SlotPublicPCommand
|
647
|
+
DESCRIPTION : Determines if an existing slot is publicly visible
|
648
|
+
for direct reference by subclasses
|
649
|
+
INPUTS : None
|
650
|
+
RETURNS : True if the slot is public, false otherwise
|
651
|
+
SIDE EFFECTS : None
|
652
|
+
NOTES : H/L Syntax : (slot-publicp <class> <slot>)
|
653
|
+
**********************************************************************/
|
654
|
+
void SlotPublicPCommand(
|
655
|
+
Environment *theEnv,
|
656
|
+
UDFContext *context,
|
657
|
+
UDFValue *returnValue)
|
658
|
+
{
|
659
|
+
Defclass *theDefclass;
|
660
|
+
SlotDescriptor *sd;
|
661
|
+
|
662
|
+
sd = CheckSlotExists(context,"slot-publicp",&theDefclass,true,false);
|
663
|
+
if (sd == NULL)
|
664
|
+
{ returnValue->lexemeValue = FalseSymbol(theEnv); }
|
665
|
+
else
|
666
|
+
{ returnValue->lexemeValue = CreateBoolean(theEnv,(sd->publicVisibility ? true : false)); }
|
667
|
+
}
|
668
|
+
|
669
|
+
/***************************************************
|
670
|
+
NAME : SlotPublicP
|
671
|
+
DESCRIPTION : Determines if a slot is public
|
672
|
+
INPUTS : 1) The class
|
673
|
+
2) The slot name
|
674
|
+
RETURNS : True if slot is public,
|
675
|
+
false otherwise
|
676
|
+
SIDE EFFECTS : None
|
677
|
+
NOTES : None
|
678
|
+
***************************************************/
|
679
|
+
bool SlotPublicP(
|
680
|
+
Defclass *theDefclass,
|
681
|
+
const char *slotName)
|
682
|
+
{
|
683
|
+
SlotDescriptor *sd;
|
684
|
+
Environment *theEnv = theDefclass->header.env;
|
685
|
+
|
686
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,false)) == NULL)
|
687
|
+
return false;
|
688
|
+
return(sd->publicVisibility ? true : false);
|
689
|
+
}
|
690
|
+
|
691
|
+
/***************************************************
|
692
|
+
NAME : SlotDefaultP
|
693
|
+
DESCRIPTION : Determines if a slot has a default value
|
694
|
+
INPUTS : 1) The class
|
695
|
+
2) The slot name
|
696
|
+
RETURNS : True if slot is public,
|
697
|
+
false otherwise
|
698
|
+
SIDE EFFECTS : None
|
699
|
+
NOTES : None
|
700
|
+
***************************************************/
|
701
|
+
int SlotDefaultP(
|
702
|
+
Environment *theEnv,
|
703
|
+
Defclass *theDefclass,
|
704
|
+
const char *slotName)
|
705
|
+
{
|
706
|
+
SlotDescriptor *sd;
|
707
|
+
|
708
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,false)) == NULL)
|
709
|
+
return(NO_DEFAULT);
|
710
|
+
|
711
|
+
if (sd->noDefault)
|
712
|
+
{ return(NO_DEFAULT); }
|
713
|
+
else if (sd->dynamicDefault)
|
714
|
+
{ return(DYNAMIC_DEFAULT); }
|
715
|
+
|
716
|
+
return(STATIC_DEFAULT);
|
717
|
+
}
|
718
|
+
|
719
|
+
|
720
|
+
/**********************************************************************
|
721
|
+
NAME : SlotDirectAccessPCommand
|
722
|
+
DESCRIPTION : Determines if an existing slot can be directly
|
723
|
+
referenced by the class - i.e., if the slot is
|
724
|
+
private, is the slot defined in the class
|
725
|
+
INPUTS : None
|
726
|
+
RETURNS : True if the slot is private,
|
727
|
+
false otherwise
|
728
|
+
SIDE EFFECTS : None
|
729
|
+
NOTES : H/L Syntax : (slot-direct-accessp <class> <slot>)
|
730
|
+
**********************************************************************/
|
731
|
+
void SlotDirectAccessPCommand(
|
732
|
+
Environment *theEnv,
|
733
|
+
UDFContext *context,
|
734
|
+
UDFValue *returnValue)
|
735
|
+
{
|
736
|
+
Defclass *theDefclass;
|
737
|
+
SlotDescriptor *sd;
|
738
|
+
|
739
|
+
sd = CheckSlotExists(context,"slot-direct-accessp",&theDefclass,true,true);
|
740
|
+
if (sd == NULL)
|
741
|
+
{ returnValue->lexemeValue = FalseSymbol(theEnv); }
|
742
|
+
else
|
743
|
+
{ returnValue->lexemeValue = CreateBoolean(theEnv,((sd->publicVisibility || (sd->cls == theDefclass)) ? true : false)); }
|
744
|
+
}
|
745
|
+
|
746
|
+
/***************************************************
|
747
|
+
NAME : SlotDirectAccessP
|
748
|
+
DESCRIPTION : Determines if a slot is directly
|
749
|
+
accessible from message-handlers
|
750
|
+
on class
|
751
|
+
INPUTS : 1) The class
|
752
|
+
2) The slot name
|
753
|
+
RETURNS : True if slot is directly
|
754
|
+
accessible, false otherwise
|
755
|
+
SIDE EFFECTS : None
|
756
|
+
NOTES : None
|
757
|
+
***************************************************/
|
758
|
+
bool SlotDirectAccessP(
|
759
|
+
Defclass *theDefclass,
|
760
|
+
const char *slotName)
|
761
|
+
{
|
762
|
+
SlotDescriptor *sd;
|
763
|
+
Environment *theEnv = theDefclass->header.env;
|
764
|
+
|
765
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,true)) == NULL)
|
766
|
+
return false;
|
767
|
+
return((sd->publicVisibility || (sd->cls == theDefclass)) ?
|
768
|
+
true : false);
|
769
|
+
}
|
770
|
+
|
771
|
+
/**********************************************************************
|
772
|
+
NAME : SlotDefaultValueCommand
|
773
|
+
DESCRIPTION : Determines the default avlue for the specified slot
|
774
|
+
of the specified class
|
775
|
+
INPUTS : None
|
776
|
+
RETURNS : Nothing useful
|
777
|
+
SIDE EFFECTS : None
|
778
|
+
NOTES : H/L Syntax : (slot-default-value <class> <slot>)
|
779
|
+
**********************************************************************/
|
780
|
+
void SlotDefaultValueCommand(
|
781
|
+
Environment *theEnv,
|
782
|
+
UDFContext *context,
|
783
|
+
UDFValue *returnValue)
|
784
|
+
{
|
785
|
+
Defclass *theDefclass;
|
786
|
+
SlotDescriptor *sd;
|
787
|
+
|
788
|
+
returnValue->lexemeValue = FalseSymbol(theEnv);
|
789
|
+
|
790
|
+
sd = CheckSlotExists(context,"slot-default-value",&theDefclass,true,true);
|
791
|
+
if (sd == NULL)
|
792
|
+
return;
|
793
|
+
|
794
|
+
if (sd->noDefault)
|
795
|
+
{
|
796
|
+
returnValue->lexemeValue = CreateSymbol(theEnv,"?NONE");
|
797
|
+
return;
|
798
|
+
}
|
799
|
+
|
800
|
+
if (sd->dynamicDefault)
|
801
|
+
EvaluateAndStoreInDataObject(theEnv,sd->multiple,
|
802
|
+
(Expression *) sd->defaultValue,
|
803
|
+
returnValue,true);
|
804
|
+
else
|
805
|
+
GenCopyMemory(UDFValue,1,returnValue,sd->defaultValue);
|
806
|
+
}
|
807
|
+
|
808
|
+
/*********************************************************
|
809
|
+
NAME : SlotDefaultValue
|
810
|
+
DESCRIPTION : Determines the default value for
|
811
|
+
the specified slot of the specified class
|
812
|
+
INPUTS : 1) The class
|
813
|
+
2) The slot name
|
814
|
+
RETURNS : True if slot default value is set,
|
815
|
+
false otherwise
|
816
|
+
SIDE EFFECTS : Slot default value evaluated - dynamic
|
817
|
+
defaults will cause any side effects
|
818
|
+
NOTES : None
|
819
|
+
*********************************************************/
|
820
|
+
bool SlotDefaultValue(
|
821
|
+
Defclass *theDefclass,
|
822
|
+
const char *slotName,
|
823
|
+
CLIPSValue *theValue)
|
824
|
+
{
|
825
|
+
SlotDescriptor *sd;
|
826
|
+
bool rv;
|
827
|
+
UDFValue result;
|
828
|
+
UDFValue *tmpPtr;
|
829
|
+
Environment *theEnv = theDefclass->header.env;
|
830
|
+
|
831
|
+
theValue->value = FalseSymbol(theEnv);
|
832
|
+
if ((sd = LookupSlot(theEnv,theDefclass,slotName,true)) == NULL)
|
833
|
+
{ return false; }
|
834
|
+
|
835
|
+
if (sd->noDefault)
|
836
|
+
{
|
837
|
+
theValue->value = CreateSymbol(theEnv,"?NONE");
|
838
|
+
return true;
|
839
|
+
}
|
840
|
+
|
841
|
+
if (sd->dynamicDefault)
|
842
|
+
{
|
843
|
+
rv = EvaluateAndStoreInDataObject(theEnv,sd->multiple,
|
844
|
+
(Expression *) sd->defaultValue,
|
845
|
+
&result,true);
|
846
|
+
NormalizeMultifield(theEnv,&result);
|
847
|
+
theValue->value = result.value;
|
848
|
+
return rv;
|
849
|
+
}
|
850
|
+
|
851
|
+
tmpPtr = (UDFValue *) sd->defaultValue;
|
852
|
+
theValue->value = tmpPtr->value;
|
853
|
+
return true;
|
854
|
+
}
|
855
|
+
|
856
|
+
/********************************************************
|
857
|
+
NAME : ClassExistPCommand
|
858
|
+
DESCRIPTION : Determines if a class exists
|
859
|
+
INPUTS : None
|
860
|
+
RETURNS : True if class exists, false otherwise
|
861
|
+
SIDE EFFECTS : None
|
862
|
+
NOTES : H/L Syntax : (class-existp <arg>)
|
863
|
+
********************************************************/
|
864
|
+
void ClassExistPCommand(
|
865
|
+
Environment *theEnv,
|
866
|
+
UDFContext *context,
|
867
|
+
UDFValue *returnValue)
|
868
|
+
{
|
869
|
+
UDFValue theArg;
|
870
|
+
|
871
|
+
if (! UDFFirstArgument(context,SYMBOL_BIT,&theArg))
|
872
|
+
{ return; }
|
873
|
+
|
874
|
+
returnValue->lexemeValue = CreateBoolean(theEnv,((LookupDefclassByMdlOrScope(theEnv,theArg.lexemeValue->contents) != NULL) ? true : false));
|
875
|
+
}
|
876
|
+
|
877
|
+
/* =========================================
|
878
|
+
*****************************************
|
879
|
+
INTERNALLY VISIBLE FUNCTIONS
|
880
|
+
=========================================
|
881
|
+
***************************************** */
|
882
|
+
|
883
|
+
/******************************************************
|
884
|
+
NAME : CheckTwoClasses
|
885
|
+
DESCRIPTION : Checks for exactly two class arguments
|
886
|
+
for a H/L function
|
887
|
+
INPUTS : 1) The function name
|
888
|
+
2) Caller's buffer for first class
|
889
|
+
3) Caller's buffer for second class
|
890
|
+
RETURNS : True if both found, false otherwise
|
891
|
+
SIDE EFFECTS : Caller's buffers set
|
892
|
+
NOTES : Assumes exactly 2 arguments
|
893
|
+
******************************************************/
|
894
|
+
static bool CheckTwoClasses(
|
895
|
+
UDFContext *context,
|
896
|
+
const char *func,
|
897
|
+
Defclass **c1,
|
898
|
+
Defclass **c2)
|
899
|
+
{
|
900
|
+
UDFValue theArg;
|
901
|
+
Environment *theEnv = context->environment;
|
902
|
+
|
903
|
+
if (! UDFFirstArgument(context,SYMBOL_BIT,&theArg))
|
904
|
+
{ return false; }
|
905
|
+
|
906
|
+
*c1 = LookupDefclassByMdlOrScope(theEnv,theArg.lexemeValue->contents);
|
907
|
+
if (*c1 == NULL)
|
908
|
+
{
|
909
|
+
ClassExistError(theEnv,func,theArg.lexemeValue->contents);
|
910
|
+
return false;
|
911
|
+
}
|
912
|
+
|
913
|
+
if (! UDFNextArgument(context,SYMBOL_BIT,&theArg))
|
914
|
+
{ return false; }
|
915
|
+
|
916
|
+
*c2 = LookupDefclassByMdlOrScope(theEnv,theArg.lexemeValue->contents);
|
917
|
+
if (*c2 == NULL)
|
918
|
+
{
|
919
|
+
ClassExistError(theEnv,func,theArg.lexemeValue->contents);
|
920
|
+
return false;
|
921
|
+
}
|
922
|
+
|
923
|
+
return true;
|
924
|
+
}
|
925
|
+
|
926
|
+
/***************************************************
|
927
|
+
NAME : CheckSlotExists
|
928
|
+
DESCRIPTION : Checks first two arguments of
|
929
|
+
a function for a valid class
|
930
|
+
and (inherited) slot
|
931
|
+
INPUTS : 1) The name of the function
|
932
|
+
2) A buffer to hold the found class
|
933
|
+
3) A flag indicating whether the
|
934
|
+
non-existence of the slot should
|
935
|
+
be an error
|
936
|
+
4) A flag indicating if the slot
|
937
|
+
can be inherited or not
|
938
|
+
RETURNS : NULL if slot not found, slot
|
939
|
+
descriptor otherwise
|
940
|
+
SIDE EFFECTS : Class buffer set if no errors,
|
941
|
+
NULL on errors
|
942
|
+
NOTES : None
|
943
|
+
***************************************************/
|
944
|
+
static SlotDescriptor *CheckSlotExists(
|
945
|
+
UDFContext *context,
|
946
|
+
const char *func,
|
947
|
+
Defclass **classBuffer,
|
948
|
+
bool existsErrorFlag,
|
949
|
+
bool inheritFlag)
|
950
|
+
{
|
951
|
+
CLIPSLexeme *ssym;
|
952
|
+
int slotIndex;
|
953
|
+
SlotDescriptor *sd;
|
954
|
+
Environment *theEnv = context->environment;
|
955
|
+
|
956
|
+
ssym = CheckClassAndSlot(context,func,classBuffer);
|
957
|
+
if (ssym == NULL)
|
958
|
+
return NULL;
|
959
|
+
|
960
|
+
slotIndex = FindInstanceTemplateSlot(theEnv,*classBuffer,ssym);
|
961
|
+
if (slotIndex == -1)
|
962
|
+
{
|
963
|
+
if (existsErrorFlag)
|
964
|
+
{
|
965
|
+
SlotExistError(theEnv,ssym->contents,func);
|
966
|
+
SetEvaluationError(theEnv,true);
|
967
|
+
}
|
968
|
+
return NULL;
|
969
|
+
}
|
970
|
+
|
971
|
+
sd = (*classBuffer)->instanceTemplate[slotIndex];
|
972
|
+
if ((sd->cls == *classBuffer) || inheritFlag)
|
973
|
+
{ return sd; }
|
974
|
+
|
975
|
+
PrintErrorID(theEnv,"CLASSEXM",1,false);
|
976
|
+
WriteString(theEnv,STDERR,"Inherited slot '");
|
977
|
+
WriteString(theEnv,STDERR,ssym->contents);
|
978
|
+
WriteString(theEnv,STDERR,"' from class ");
|
979
|
+
PrintClassName(theEnv,STDERR,sd->cls,true,false);
|
980
|
+
WriteString(theEnv,STDERR," is not valid for function '");
|
981
|
+
WriteString(theEnv,STDERR,func);
|
982
|
+
WriteString(theEnv,STDERR,"'.\n");
|
983
|
+
SetEvaluationError(theEnv,true);
|
984
|
+
return NULL;
|
985
|
+
}
|
986
|
+
|
987
|
+
/***************************************************
|
988
|
+
NAME : LookupSlot
|
989
|
+
DESCRIPTION : Finds a slot in a class
|
990
|
+
INPUTS : 1) The class
|
991
|
+
2) The slot name
|
992
|
+
3) A flag indicating if inherited
|
993
|
+
slots are OK or not
|
994
|
+
RETURNS : The slot descriptor address, or
|
995
|
+
NULL if not found
|
996
|
+
SIDE EFFECTS : None
|
997
|
+
NOTES : None
|
998
|
+
***************************************************/
|
999
|
+
static SlotDescriptor *LookupSlot(
|
1000
|
+
Environment *theEnv,
|
1001
|
+
Defclass *theDefclass,
|
1002
|
+
const char *slotName,
|
1003
|
+
bool inheritFlag)
|
1004
|
+
{
|
1005
|
+
CLIPSLexeme *slotSymbol;
|
1006
|
+
int slotIndex;
|
1007
|
+
SlotDescriptor *sd;
|
1008
|
+
|
1009
|
+
slotSymbol = FindSymbolHN(theEnv,slotName,SYMBOL_BIT);
|
1010
|
+
if (slotSymbol == NULL)
|
1011
|
+
{ return NULL; }
|
1012
|
+
|
1013
|
+
slotIndex = FindInstanceTemplateSlot(theEnv,theDefclass,slotSymbol);
|
1014
|
+
if (slotIndex == -1)
|
1015
|
+
{ return NULL; }
|
1016
|
+
|
1017
|
+
sd = theDefclass->instanceTemplate[slotIndex];
|
1018
|
+
if ((sd->cls != theDefclass) && (inheritFlag == false))
|
1019
|
+
{ return NULL; }
|
1020
|
+
|
1021
|
+
return sd;
|
1022
|
+
}
|
1023
|
+
|
1024
|
+
#if DEBUGGING_FUNCTIONS
|
1025
|
+
|
1026
|
+
/*****************************************************
|
1027
|
+
NAME : CheckClass
|
1028
|
+
DESCRIPTION : Used for to check class name for
|
1029
|
+
class accessor functions such
|
1030
|
+
as ppdefclass and undefclass
|
1031
|
+
INPUTS : 1) The name of the H/L function
|
1032
|
+
2) Name of the class
|
1033
|
+
RETURNS : The class address,
|
1034
|
+
or NULL if ther was an error
|
1035
|
+
SIDE EFFECTS : None
|
1036
|
+
NOTES : None
|
1037
|
+
******************************************************/
|
1038
|
+
static Defclass *CheckClass(
|
1039
|
+
Environment *theEnv,
|
1040
|
+
const char *func,
|
1041
|
+
const char *cname)
|
1042
|
+
{
|
1043
|
+
Defclass *cls;
|
1044
|
+
|
1045
|
+
cls = LookupDefclassByMdlOrScope(theEnv,cname);
|
1046
|
+
if (cls == NULL)
|
1047
|
+
ClassExistError(theEnv,func,cname);
|
1048
|
+
return(cls);
|
1049
|
+
}
|
1050
|
+
|
1051
|
+
/*********************************************************
|
1052
|
+
NAME : GetClassNameArgument
|
1053
|
+
DESCRIPTION : Gets a class name-string
|
1054
|
+
INPUTS : Calling function name
|
1055
|
+
RETURNS : Class name (NULL on errors)
|
1056
|
+
SIDE EFFECTS : None
|
1057
|
+
NOTES : Assumes only 1 argument
|
1058
|
+
*********************************************************/
|
1059
|
+
static const char *GetClassNameArgument(
|
1060
|
+
UDFContext *context)
|
1061
|
+
{
|
1062
|
+
UDFValue theArg;
|
1063
|
+
|
1064
|
+
if (! UDFFirstArgument(context,SYMBOL_BIT,&theArg))
|
1065
|
+
{ return NULL; }
|
1066
|
+
|
1067
|
+
return theArg.lexemeValue->contents;
|
1068
|
+
}
|
1069
|
+
|
1070
|
+
/****************************************************************
|
1071
|
+
NAME : PrintClassBrowse
|
1072
|
+
DESCRIPTION : Displays a "graph" of class and subclasses
|
1073
|
+
INPUTS : 1) The logical name of the output
|
1074
|
+
2) The class address
|
1075
|
+
3) The depth of the graph
|
1076
|
+
RETURNS : Nothing useful
|
1077
|
+
SIDE EFFECTS : None
|
1078
|
+
NOTES : None
|
1079
|
+
****************************************************************/
|
1080
|
+
static void PrintClassBrowse(
|
1081
|
+
Environment *theEnv,
|
1082
|
+
const char *logicalName,
|
1083
|
+
Defclass *cls,
|
1084
|
+
unsigned long depth)
|
1085
|
+
{
|
1086
|
+
unsigned long i;
|
1087
|
+
|
1088
|
+
for (i = 0 ; i < depth ; i++)
|
1089
|
+
WriteString(theEnv,logicalName," ");
|
1090
|
+
WriteString(theEnv,logicalName,DefclassName(cls));
|
1091
|
+
if (cls->directSuperclasses.classCount > 1)
|
1092
|
+
WriteString(theEnv,logicalName," *");
|
1093
|
+
WriteString(theEnv,logicalName,"\n");
|
1094
|
+
for (i = 0 ;i < cls->directSubclasses.classCount ; i++)
|
1095
|
+
PrintClassBrowse(theEnv,logicalName,cls->directSubclasses.classArray[i],depth+1);
|
1096
|
+
}
|
1097
|
+
|
1098
|
+
/*********************************************************
|
1099
|
+
NAME : DisplaySeparator
|
1100
|
+
DESCRIPTION : Prints a separator line for DescribeClass
|
1101
|
+
INPUTS : 1) The logical name of the output
|
1102
|
+
2) The buffer to use for the line
|
1103
|
+
3) The buffer size
|
1104
|
+
4) The character to use
|
1105
|
+
RETURNS : Nothing useful
|
1106
|
+
SIDE EFFECTS : Buffer overwritten and displayed
|
1107
|
+
NOTES : None
|
1108
|
+
*********************************************************/
|
1109
|
+
static void DisplaySeparator(
|
1110
|
+
Environment *theEnv,
|
1111
|
+
const char *logicalName,
|
1112
|
+
char *buf,
|
1113
|
+
int maxlen,
|
1114
|
+
int sepchar)
|
1115
|
+
{
|
1116
|
+
int i;
|
1117
|
+
|
1118
|
+
for (i = 0 ; i < maxlen-2 ; i++)
|
1119
|
+
buf[i] = (char) sepchar;
|
1120
|
+
buf[i++] = '\n';
|
1121
|
+
buf[i] = '\0';
|
1122
|
+
WriteString(theEnv,logicalName,buf);
|
1123
|
+
}
|
1124
|
+
|
1125
|
+
/*************************************************************
|
1126
|
+
NAME : DisplaySlotBasicInfo
|
1127
|
+
DESCRIPTION : Displays a table summary of basic
|
1128
|
+
facets for the slots of a class
|
1129
|
+
including:
|
1130
|
+
single/multiple
|
1131
|
+
default/no-default/default-dynamic
|
1132
|
+
inherit/no-inherit
|
1133
|
+
read-write/initialize-only/read-only
|
1134
|
+
local/shared
|
1135
|
+
composite/exclusive
|
1136
|
+
reactive/non-reactive
|
1137
|
+
public/private
|
1138
|
+
create-accessor read/write
|
1139
|
+
override-message
|
1140
|
+
|
1141
|
+
The function also displays the source
|
1142
|
+
class(es) for the facets
|
1143
|
+
INPUTS : 1) The logical name of the output
|
1144
|
+
2) A format string for use in sprintf
|
1145
|
+
(for printing slot names)
|
1146
|
+
3) A format string for use in sprintf
|
1147
|
+
(for printing slot override message names)
|
1148
|
+
4) A buffer to store the display in
|
1149
|
+
5) A pointer to the class
|
1150
|
+
RETURNS : Nothing useful
|
1151
|
+
SIDE EFFECTS : Buffer written to and displayed
|
1152
|
+
NOTES : None
|
1153
|
+
*************************************************************/
|
1154
|
+
static void DisplaySlotBasicInfo(
|
1155
|
+
Environment *theEnv,
|
1156
|
+
const char *logicalName,
|
1157
|
+
const char *slotNamePrintFormat,
|
1158
|
+
const char *overrideMessagePrintFormat,
|
1159
|
+
char *buf,
|
1160
|
+
Defclass *cls)
|
1161
|
+
{
|
1162
|
+
long i;
|
1163
|
+
SlotDescriptor *sp;
|
1164
|
+
const char *createString;
|
1165
|
+
|
1166
|
+
gensprintf(buf,slotNamePrintFormat,"SLOTS");
|
1167
|
+
#if DEFRULE_CONSTRUCT
|
1168
|
+
genstrcat(buf,"FLD DEF PRP ACC STO MCH SRC VIS CRT ");
|
1169
|
+
#else
|
1170
|
+
genstrcat(buf,"FLD DEF PRP ACC STO SRC VIS CRT ");
|
1171
|
+
#endif
|
1172
|
+
WriteString(theEnv,logicalName,buf);
|
1173
|
+
gensprintf(buf,overrideMessagePrintFormat,"OVRD-MSG");
|
1174
|
+
WriteString(theEnv,logicalName,buf);
|
1175
|
+
WriteString(theEnv,logicalName,"SOURCE(S)\n");
|
1176
|
+
for (i = 0 ; i < cls->instanceSlotCount ; i++)
|
1177
|
+
{
|
1178
|
+
sp = cls->instanceTemplate[i];
|
1179
|
+
gensprintf(buf,slotNamePrintFormat,sp->slotName->name->contents);
|
1180
|
+
genstrcat(buf,sp->multiple ? "MLT " : "SGL ");
|
1181
|
+
if (sp->noDefault)
|
1182
|
+
genstrcat(buf,"NIL ");
|
1183
|
+
else
|
1184
|
+
genstrcat(buf,sp->dynamicDefault ? "DYN " : "STC ");
|
1185
|
+
genstrcat(buf,sp->noInherit ? "NIL " : "INH ");
|
1186
|
+
if (sp->initializeOnly)
|
1187
|
+
genstrcat(buf,"INT ");
|
1188
|
+
else if (sp->noWrite)
|
1189
|
+
genstrcat(buf," R ");
|
1190
|
+
else
|
1191
|
+
genstrcat(buf,"RW ");
|
1192
|
+
genstrcat(buf,sp->shared ? "SHR " : "LCL ");
|
1193
|
+
#if DEFRULE_CONSTRUCT
|
1194
|
+
genstrcat(buf,sp->reactive ? "RCT " : "NIL ");
|
1195
|
+
#endif
|
1196
|
+
genstrcat(buf,sp->composite ? "CMP " : "EXC ");
|
1197
|
+
genstrcat(buf,sp->publicVisibility ? "PUB " : "PRV ");
|
1198
|
+
createString = GetCreateAccessorString(sp);
|
1199
|
+
if (createString[1] == '\0')
|
1200
|
+
genstrcat(buf," ");
|
1201
|
+
genstrcat(buf,createString);
|
1202
|
+
if ((createString[1] == '\0') ? true : (createString[2] == '\0'))
|
1203
|
+
genstrcat(buf," ");
|
1204
|
+
genstrcat(buf," ");
|
1205
|
+
WriteString(theEnv,logicalName,buf);
|
1206
|
+
gensprintf(buf,overrideMessagePrintFormat,
|
1207
|
+
sp->noWrite ? "NIL" : sp->overrideMessage->contents);
|
1208
|
+
WriteString(theEnv,logicalName,buf);
|
1209
|
+
PrintSlotSources(theEnv,logicalName,sp->slotName->name,&sp->cls->allSuperclasses,0,true);
|
1210
|
+
WriteString(theEnv,logicalName,"\n");
|
1211
|
+
}
|
1212
|
+
}
|
1213
|
+
|
1214
|
+
/***************************************************
|
1215
|
+
NAME : PrintSlotSources
|
1216
|
+
DESCRIPTION : Displays a list of source classes
|
1217
|
+
for a composite class (in order
|
1218
|
+
of most general to specific)
|
1219
|
+
INPUTS : 1) The logical name of the output
|
1220
|
+
2) The name of the slot
|
1221
|
+
3) The precedence list of the class
|
1222
|
+
of the slot (the source class
|
1223
|
+
shold be first in the list)
|
1224
|
+
4) The index into the packed
|
1225
|
+
links array
|
1226
|
+
5) Flag indicating whether to
|
1227
|
+
disregard noniherit facet
|
1228
|
+
RETURNS : True if a class is printed, false
|
1229
|
+
otherwise
|
1230
|
+
SIDE EFFECTS : Recursively prints out appropriate
|
1231
|
+
memebers from list in reverse order
|
1232
|
+
NOTES : None
|
1233
|
+
***************************************************/
|
1234
|
+
static bool PrintSlotSources(
|
1235
|
+
Environment *theEnv,
|
1236
|
+
const char *logicalName,
|
1237
|
+
CLIPSLexeme *sname,
|
1238
|
+
PACKED_CLASS_LINKS *sprec,
|
1239
|
+
unsigned long theIndex,
|
1240
|
+
bool inhp)
|
1241
|
+
{
|
1242
|
+
SlotDescriptor *csp;
|
1243
|
+
|
1244
|
+
if (theIndex == sprec->classCount)
|
1245
|
+
return false;
|
1246
|
+
csp = FindClassSlot(sprec->classArray[theIndex],sname);
|
1247
|
+
if ((csp != NULL) ? ((csp->noInherit == 0) || inhp) : false)
|
1248
|
+
{
|
1249
|
+
if (csp->composite)
|
1250
|
+
{
|
1251
|
+
if (PrintSlotSources(theEnv,logicalName,sname,sprec,theIndex+1,false))
|
1252
|
+
WriteString(theEnv,logicalName," ");
|
1253
|
+
}
|
1254
|
+
PrintClassName(theEnv,logicalName,sprec->classArray[theIndex],false,false);
|
1255
|
+
return true;
|
1256
|
+
}
|
1257
|
+
else
|
1258
|
+
return(PrintSlotSources(theEnv,logicalName,sname,sprec,theIndex+1,false));
|
1259
|
+
}
|
1260
|
+
|
1261
|
+
/*********************************************************
|
1262
|
+
NAME : DisplaySlotConstraintInfo
|
1263
|
+
DESCRIPTION : Displays a table summary of type-checking
|
1264
|
+
facets for the slots of a class
|
1265
|
+
including:
|
1266
|
+
type
|
1267
|
+
allowed-symbols
|
1268
|
+
allowed-integers
|
1269
|
+
allowed-floats
|
1270
|
+
allowed-values
|
1271
|
+
allowed-instance-names
|
1272
|
+
range
|
1273
|
+
min-number-of-elements
|
1274
|
+
max-number-of-elements
|
1275
|
+
|
1276
|
+
The function also displays the source
|
1277
|
+
class(es) for the facets
|
1278
|
+
INPUTS : 1) A format string for use in sprintf
|
1279
|
+
2) A buffer to store the display in
|
1280
|
+
3) Maximum buffer size
|
1281
|
+
4) A pointer to the class
|
1282
|
+
RETURNS : Nothing useful
|
1283
|
+
SIDE EFFECTS : Buffer written to and displayed
|
1284
|
+
NOTES : None
|
1285
|
+
*********************************************************/
|
1286
|
+
static void DisplaySlotConstraintInfo(
|
1287
|
+
Environment *theEnv,
|
1288
|
+
const char *logicalName,
|
1289
|
+
const char *slotNamePrintFormat,
|
1290
|
+
char *buf,
|
1291
|
+
unsigned maxlen,
|
1292
|
+
Defclass *cls)
|
1293
|
+
{
|
1294
|
+
long i;
|
1295
|
+
CONSTRAINT_RECORD *cr;
|
1296
|
+
const char *strdest = "***describe-class***";
|
1297
|
+
|
1298
|
+
gensprintf(buf,slotNamePrintFormat,"SLOTS");
|
1299
|
+
genstrcat(buf,"SYM STR INN INA EXA FTA INT FLT\n");
|
1300
|
+
WriteString(theEnv,logicalName,buf);
|
1301
|
+
for (i = 0 ; i < cls->instanceSlotCount ; i++)
|
1302
|
+
{
|
1303
|
+
cr = cls->instanceTemplate[i]->constraint;
|
1304
|
+
gensprintf(buf,slotNamePrintFormat,cls->instanceTemplate[i]->slotName->name->contents);
|
1305
|
+
if (cr != NULL)
|
1306
|
+
{
|
1307
|
+
genstrcat(buf,ConstraintCode(cr,cr->symbolsAllowed,cr->symbolRestriction));
|
1308
|
+
genstrcat(buf,ConstraintCode(cr,cr->stringsAllowed,cr->stringRestriction));
|
1309
|
+
genstrcat(buf,ConstraintCode(cr,cr->instanceNamesAllowed,
|
1310
|
+
(cr->instanceNameRestriction || cr->classRestriction)));
|
1311
|
+
genstrcat(buf,ConstraintCode(cr,cr->instanceAddressesAllowed,cr->classRestriction));
|
1312
|
+
genstrcat(buf,ConstraintCode(cr,cr->externalAddressesAllowed,0));
|
1313
|
+
genstrcat(buf,ConstraintCode(cr,cr->factAddressesAllowed,0));
|
1314
|
+
genstrcat(buf,ConstraintCode(cr,cr->integersAllowed,cr->integerRestriction));
|
1315
|
+
genstrcat(buf,ConstraintCode(cr,cr->floatsAllowed,cr->floatRestriction));
|
1316
|
+
OpenStringDestination(theEnv,strdest,buf + strlen(buf),(maxlen - strlen(buf) - 1));
|
1317
|
+
if (cr->integersAllowed || cr->floatsAllowed || cr->anyAllowed)
|
1318
|
+
{
|
1319
|
+
WriteString(theEnv,strdest,"RNG:[");
|
1320
|
+
PrintExpression(theEnv,strdest,cr->minValue);
|
1321
|
+
WriteString(theEnv,strdest,"..");
|
1322
|
+
PrintExpression(theEnv,strdest,cr->maxValue);
|
1323
|
+
WriteString(theEnv,strdest,"] ");
|
1324
|
+
}
|
1325
|
+
if (cls->instanceTemplate[i]->multiple)
|
1326
|
+
{
|
1327
|
+
WriteString(theEnv,strdest,"CRD:[");
|
1328
|
+
PrintExpression(theEnv,strdest,cr->minFields);
|
1329
|
+
WriteString(theEnv,strdest,"..");
|
1330
|
+
PrintExpression(theEnv,strdest,cr->maxFields);
|
1331
|
+
WriteString(theEnv,strdest,"]");
|
1332
|
+
}
|
1333
|
+
}
|
1334
|
+
else
|
1335
|
+
{
|
1336
|
+
OpenStringDestination(theEnv,strdest,buf,maxlen);
|
1337
|
+
WriteString(theEnv,strdest," + + + + + + + + RNG:[-oo..+oo]");
|
1338
|
+
if (cls->instanceTemplate[i]->multiple)
|
1339
|
+
WriteString(theEnv,strdest," CRD:[0..+oo]");
|
1340
|
+
}
|
1341
|
+
WriteString(theEnv,strdest,"\n");
|
1342
|
+
CloseStringDestination(theEnv,strdest);
|
1343
|
+
WriteString(theEnv,logicalName,buf);
|
1344
|
+
}
|
1345
|
+
}
|
1346
|
+
|
1347
|
+
/******************************************************
|
1348
|
+
NAME : ConstraintCode
|
1349
|
+
DESCRIPTION : Gives a string code representing the
|
1350
|
+
type of constraint
|
1351
|
+
INPUTS : 1) The constraint record
|
1352
|
+
2) Allowed Flag
|
1353
|
+
3) Restricted Values flag
|
1354
|
+
RETURNS : " " for type not allowed
|
1355
|
+
" + " for any value of type allowed
|
1356
|
+
" # " for some values of type allowed
|
1357
|
+
SIDE EFFECTS : None
|
1358
|
+
NOTES : Used by DisplaySlotConstraintInfo
|
1359
|
+
******************************************************/
|
1360
|
+
static const char *ConstraintCode(
|
1361
|
+
CONSTRAINT_RECORD *cr,
|
1362
|
+
unsigned allow,
|
1363
|
+
unsigned restrictValues)
|
1364
|
+
{
|
1365
|
+
if (allow || cr->anyAllowed)
|
1366
|
+
{
|
1367
|
+
if (restrictValues || cr->anyRestriction) return " # ";
|
1368
|
+
else return " + ";
|
1369
|
+
}
|
1370
|
+
return(" ");
|
1371
|
+
}
|
1372
|
+
|
1373
|
+
#endif
|
1374
|
+
|
1375
|
+
#endif
|
1376
|
+
|