00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027 #define EXPORT_BORLAND
00028
00029 #ifdef IS_DLL
00030 #define EXPORT_MSCPP __declspec(dllexport)
00031 #else
00032 #define EXPORT_MSCPP
00033 #endif
00034
00035
00036
00037
00038 #ifndef lint
00039
00040 #endif
00041
00042
00043
00044
00045
00046
00047 #include <stdio.h>
00048 #include <stdlib.h>
00049 #include <string.h>
00050
00051 #include <stdarg.h>
00052 #include <ctype.h>
00053 #include "libicl.h"
00054 #include "libutils.h"
00055 #include "libicl_private.h"
00056 #include "libicl_depr.h"
00057 #include "stdpccts.h"
00058
00059 #ifdef _WINDOWS
00060 #include "oaa-windows.h"
00061 #endif
00062
00063
00064
00065
00066
00067 extern char* ICLDATAQSTART;
00068 extern size_t ICLDATAQSTARTLEN;
00069 static int rename_vars_index;
00070
00071 #ifndef STREQ
00072 #define STREQ(str1, str2) (strcmp((str1), (str2)) == 0)
00073 #endif
00074
00075 #ifdef NORMAL_GC
00076 char* gc_strdup(char* s)
00077 {
00078 int i = strlen(s);
00079 char* p = (char*)malloc(i + 1);
00080 strcpy(p, s);
00081 p[i] = '\0';
00082 return p;
00083 }
00084 #endif
00085
00086
00087
00088
00089
00090
00091
00092
00093 static void icl_deref(ICLTerm **var, struct dyn_array var_bindings);
00094 static ICLListType *
00095 icl_copy_list_type(ICLListType *list, struct dyn_array *vars);
00096
00097 EXTERN void printDebug(int level, char *str, ...);
00098
00099
00100
00101
00102 static void iclIncRef(ICLTerm* t);
00103 int iclDecRef(ICLTerm* t);
00104 static void icl_FreeTermMulti(ICLTerm *elt, int n, void* pc);
00105
00106
00107
00108
00109
00110 static void iclIncRef(ICLTerm* t)
00111 {
00112 t->refCount++;
00113 }
00114
00120 int iclDecRef(ICLTerm* t)
00121 {
00122 if(t != NULL) {
00123 t->refCount -= 1;
00124 return t->refCount;
00125 }
00126 return -1;
00127 }
00128
00132 EXPORT_MSCPP
00133 void EXPORT_BORLAND icl_init_const_dyn_array(struct const_dyn_array *da)
00134 {
00135 (*da).allocated = 0;
00136 (*da).count = 0;
00137 (*da).item = NULL;
00138 }
00142 EXPORT_MSCPP
00143 void EXPORT_BORLAND icl_init_dyn_array(struct dyn_array *da)
00144 {
00145 (*da).allocated = 0;
00146 (*da).count = 0;
00147 (*da).item = NULL;
00148 }
00149
00155 EXPORT_MSCPP
00156 int EXPORT_BORLAND
00157 icl_stIsVar(char *t)
00158 {
00159 return ((t != NULL) && ((*t == '_') || ((*t >= 'A') && (*t <= 'Z'))));
00160 }
00161
00162 EXPORT_MSCPP
00163 int EXPORT_BORLAND
00164 icl_stIsOperation(char *t){
00165 return icl_stOperationArgs(t, NULL, NULL, NULL);
00166 }
00167
00168 EXPORT_MSCPP
00169 int EXPORT_BORLAND
00170 icl_stIsIclDataQ(char* t, size_t len)
00171 {
00172 static size_t dataqMarkerLen = 0;
00173 if(dataqMarkerLen == 0) {
00174 dataqMarkerLen = strlen(ICLDATAQSTART);
00175 }
00176 if(len >= 9) {
00177 if(strncmp(t, ICLDATAQSTART, dataqMarkerLen) == 0) {
00178 return TRUE;
00179 }
00180 }
00181
00182 return FALSE;
00183 }
00184
00190 EXPORT_MSCPP
00191 int EXPORT_BORLAND
00192 icl_stIsInt(char *t)
00193 {
00194 char *p;
00195
00196 strtol(t, &p, 10);
00197 return ((p != t) && (*p == '\0'));
00198 }
00199
00200
00206 EXPORT_MSCPP
00207 int EXPORT_BORLAND
00208 icl_stIsFloat(char *t)
00209 {
00210 char *p;
00211
00212 strtod(t, &p);
00213 if (p == t)
00214 return (FALSE);
00215
00216 if (*p == '\0')
00217 return (TRUE);
00218
00219 if ((*p == 'E'))
00220 return (((*(p+1) == '+') ||
00221 (*(p+1) == '-')) &&
00222 (atoi(p+2) > 0));
00223 else return (FALSE);
00224 }
00225
00232 EXPORT_MSCPP
00233 void EXPORT_BORLAND
00234 icl_stUndoubleQuotes(char *s)
00235 {
00236 char c;
00237 char cc;
00238 char* in_ptr;
00239 char* out_ptr;
00240
00241 in_ptr = s;
00242 out_ptr = s;
00243
00244 while ((c = *in_ptr++) != (char) NULL) {
00245 cc = *in_ptr;
00246 if (c == '\'' && cc == c) {
00247 *out_ptr++ = c;
00248 in_ptr++;
00249 } else {
00250 *out_ptr++ = c;
00251 }
00252 }
00253 *out_ptr++ = '\0';
00254 }
00255
00267 EXPORT_MSCPP
00268 char * EXPORT_BORLAND
00269 icl_stFixQuotes(char *s)
00270 {
00271 icl_stRemoveQuotes(s);
00272 icl_stUndoubleQuotes(s);
00273 return s;
00274 }
00275
00276
00277
00288 EXPORT_MSCPP
00289 char * EXPORT_BORLAND
00290 icl_stDoubleQuotes(char *s)
00291 {
00292 static char *out_str = 0;
00293 static int out_str_len = 0;
00294 char *in_ptr, *out_ptr;
00295 char c;
00296 int i = 0;
00297 int num = 0;
00298 int new_len;
00299
00300
00301 while (i < (int)strlen(s)) {
00302 if (s[i] == '\'') {
00303 num++;
00304 }
00305 i++;
00306 }
00307
00308 new_len = strlen(s) + num + 10;
00309
00310
00311 if (out_str_len < new_len) {
00312 if (out_str) {
00313 icl_stFree(out_str);
00314 }
00315 out_str = malloc(new_len);
00316 out_str_len = new_len;
00317 }
00318
00319
00320 in_ptr = s;
00321 out_ptr = out_str;
00322 while ((c = *in_ptr++) != 0) {
00323 if (c == '\'') {
00324 *out_ptr++ = c;
00325 *out_ptr++ = c;
00326 } else {
00327 *out_ptr++ = c;
00328 }
00329 }
00330 *out_ptr++ = (char) 0;
00331
00332 return out_str;
00333
00334 }
00335
00336
00346 EXPORT_MSCPP
00347 char * EXPORT_BORLAND
00348 icl_stQuoteForce(char *s)
00349 {
00350 static char *out_str = 0;
00351 static int out_str_len = 0;
00352
00353
00354 char *in_ptr, *out_ptr;
00355 char c;
00356 int i = 0;
00357 int num = 0;
00358 int new_len;
00359
00360
00361 while (i < (int)strlen(s)) {
00362 if (s[i] == '\'') {
00363 num++;
00364 }
00365 i++;
00366 }
00367
00368 new_len = strlen(s) + num + 10;
00369
00370
00371 if (out_str_len < new_len) {
00372 if (out_str) {
00373 icl_stFree(out_str);
00374 }
00375 out_str = malloc(new_len);
00376 out_str_len = new_len;
00377 }
00378
00379
00380 in_ptr = s;
00381 out_ptr = out_str;
00382 *out_ptr++ = '\'';
00383 while ((c = *in_ptr++) != 0) {
00384 if (c == '\'') {
00385 *out_ptr++ = c;
00386 *out_ptr++ = c;
00387 } else {
00388 *out_ptr++ = c;
00389 }
00390 }
00391 *out_ptr++ = '\'';
00392 *out_ptr++ = (char) 0;
00393
00394 return (out_str);
00395 }
00396
00406 EXPORT_MSCPP
00407 char * EXPORT_BORLAND
00408 icl_stQuote(char *s)
00409 {
00410 static char *out_str = 0;
00411 static int out_str_len = 0;
00412
00413 if (icl_stIsStr(s))
00414 return (s);
00415
00416
00417 else {
00418 char *in_ptr, *out_ptr;
00419 char c;
00420 int i = 0;
00421 int num = 0;
00422 int new_len;
00423
00424
00425 while (i < (int)strlen(s)) {
00426 if (s[i] == '\'') {
00427 num++;
00428 }
00429 i++;
00430 }
00431
00432 new_len = strlen(s) + num + 10;
00433
00434
00435 if (out_str_len < new_len) {
00436 if (out_str) {
00437 icl_stFree(out_str);
00438 }
00439 out_str = malloc(new_len);
00440 out_str_len = new_len;
00441 }
00442
00443
00444 in_ptr = s;
00445 out_ptr = out_str;
00446 *out_ptr++ = '\'';
00447 while ((c = *in_ptr++) != 0) {
00448 if (c == '\'') {
00449 *out_ptr++ = c;
00450 *out_ptr++ = c;
00451 } else {
00452 *out_ptr++ = c;
00453 }
00454 }
00455 *out_ptr++ = '\'';
00456 *out_ptr++ = (char) 0;
00457
00458 return (out_str);
00459 }
00460 }
00461
00462
00463
00464
00465
00470 EXPORT_MSCPP
00471 void EXPORT_BORLAND
00472 icl_stTrim(char *s)
00473 {
00474 while (s && (*s) && (*s <= ' '))
00475 strcpy(s, &s[1]);
00476 while (s && (*s) && (s[strlen(s)-1] <= ' '))
00477 s[strlen(s)-1] = '\0';
00478 }
00479
00480
00481
00491 EXPORT_MSCPP
00492 void EXPORT_BORLAND
00493 icl_stAppend(char **str1, char *str2)
00494 {
00495 char *p;
00496 int str2len = strlen(str2);
00497
00498 if (!str2 || !*str2) return;
00499
00500 if (*str1 == NULL) {
00501
00502 *str1 = (char*)malloc(sizeof(char) * (str2len + 1));
00503 *str1 = strdup(str2);
00504 (*str1)[str2len] = '\0';
00505 }
00506 else {
00507 p = malloc(strlen(*str1) + strlen(str2)+1);
00508 strcpy(p, *str1);
00509 strcat(p, str2);
00510 icl_stFree(*str1);
00511 *str1 = p;
00512 }
00513 }
00514
00515
00516
00517
00518
00519 static
00520 void icl_rename_vars_termhelper(ICLTerm **term, hthash_table *knownVars)
00521 {
00522 ICLListType *l;
00523 char *hashedVal = NULL;
00524
00525
00526 if (icl_IsValid(*term)) {
00527 if (icl_IsVar(*term)) {
00528 if((strncmp((*term)->p,"_",1) == 0) &&
00529 (strlen((*term)->p) == 1)) {
00530 char tempName[10];
00531 hashedVal = NULL;
00532 do {
00533 sprintf(tempName, "_%d", rename_vars_index++);
00534 }
00535 while((hashedVal = (char*)htlookup(tempName, knownVars)) != NULL);
00536 free((*term)->p);
00537 (*term)->p = strdup(tempName);
00538 }
00539 else {
00540 hashedVal = (char *)htlookup((char *)((*term)->p), knownVars);
00541 }
00542 if(hashedVal != NULL) {
00543 free((*term)->p);
00544 (*term)->p = strdup(hashedVal);
00545 }
00546 else {
00547 char tempName[10];
00548 sprintf(tempName, "_%d", rename_vars_index);
00549 rename_vars_index++;
00550 htinsert((char *)((*term)->p),strdup(tempName),knownVars);
00551 free((*term)->p);
00552 (*term)->p = strdup(tempName);
00553 }
00554 }
00555 else
00556 if (((*term)->iclType == icl_list_type) ||
00557 ((*term)->iclType == icl_group_type) ||
00558 ((*term)->iclType == icl_struct_type)) {
00559 l = icl_List(*term);
00560
00561 while (l) {
00562 icl_rename_vars_termhelper(&l->elt, knownVars);
00563 l = l->next;
00564 }
00565 }
00566 }
00567 }
00568
00573 static
00574 void icl_rename_vars_term(ICLTerm **term)
00575 {
00576 hthash_table knownVars;
00577 htconstruct_table(&knownVars, 271);
00578 icl_rename_vars_termhelper(term, &knownVars);
00579 #ifdef NORMAL_GC
00580 htfree_table(&knownVars,GC_debug_free);
00581 #else
00582 htfree_table(&knownVars,free);
00583 #endif
00584 }
00585
00586
00587
00588
00589
00590
00591
00592
00593
00594
00595
00596 struct compoundInfo_s
00597 {
00598 guint8* preChild;
00599 size_t preChildLen;
00600 guint8* postChild;
00601 size_t postChildLen;
00602 guint8* preAllButFirst;
00603 size_t preAllButFirstLen;
00604 guint8* postAllButLast;
00605 size_t postAllButLastLen;
00606 guint8* postPend;
00607 size_t postPendLen;
00608 int numChildrenToDo;
00609 int originalNumChildren;
00610 }
00611 ;
00612 typedef struct compoundInfo_s compoundInfo_t;
00613
00614 compoundInfo_t* compoundInfo_new()
00615 {
00616 compoundInfo_t* res = (compoundInfo_t*)malloc(sizeof(compoundInfo_t));
00617 memset(res, 0, sizeof(compoundInfo_t));
00618 return res;
00619 }
00620
00621 int compoundInfo_finished(compoundInfo_t* ci)
00622 {
00623 if(ci->numChildrenToDo == 0) {
00624 return TRUE;
00625 }
00626 else {
00627 return FALSE;
00628 }
00629 }
00630
00631 void compoundInfo_setNumChildren(compoundInfo_t* ci, int n)
00632 {
00633 ci->numChildrenToDo = n;
00634 ci->originalNumChildren = n;
00635 }
00636
00637 int compoundInfo_getCurrentChildNum(compoundInfo_t* ci)
00638 {
00639 return ci->originalNumChildren - ci->numChildrenToDo;
00640 }
00641
00642 void compoundInfo_setPreAllButFirst(compoundInfo_t* ci, guint8* s, size_t len)
00643 {
00644 ci->preAllButFirst = s;
00645 ci->preAllButFirstLen = len;
00646 }
00647
00648 void compoundInfo_setPostAllButLast(compoundInfo_t* ci, guint8* s, size_t len)
00649 {
00650 ci->postAllButLast = s;
00651 ci->postAllButLastLen = len;
00652 }
00653
00654 void compoundInfo_setPreChild(compoundInfo_t* ci, guint8* s, size_t len)
00655 {
00656 ci->preChild = s;
00657 ci->preChildLen = len;
00658 }
00659
00660 void compoundInfo_setPostChild(compoundInfo_t* ci, guint8* s, size_t len)
00661 {
00662 ci->postChild = s;
00663 ci->postChildLen = len;
00664 }
00665
00666 void compoundInfo_setPostPend(compoundInfo_t* ci, guint8* s, size_t len)
00667 {
00668 ci->postPend = s;
00669 ci->postPendLen = len;
00670 }
00671
00672 guint8* compoundInfo_getPreChild(compoundInfo_t* ci, int i, size_t* len)
00673 {
00674 if(ci->preAllButFirst != NULL) {
00675 if(i != 0) {
00676 *len = ci->preAllButFirstLen;
00677 return ci->preAllButFirst;
00678 }
00679 else {
00680 *len = 0;
00681 return NULL;
00682 }
00683 }
00684 else {
00685 *len = ci->preChildLen;
00686 return ci->preChild;
00687 }
00688 }
00689
00690 guint8* compoundInfo_getPostChild(compoundInfo_t* ci, int i, size_t* len)
00691 {
00692 if(ci->postAllButLast != NULL) {
00693 if(i != ci->originalNumChildren - 1) {
00694 *len = ci->postAllButLastLen;
00695 return ci->postAllButLast;
00696 }
00697 else {
00698 *len = 0;
00699 return NULL;
00700 }
00701 }
00702 else {
00703 *len = ci->postChildLen;
00704 return ci->postChild;
00705 }
00706 }
00707
00708 guint8* compoundInfo_getPostPend(compoundInfo_t* ci, size_t* len)
00709 {
00710 *len = ci->postPendLen;
00711 return ci->postPend;
00712 }
00713
00714 void compoundInfo_childFinished(compoundInfo_t* ci)
00715 {
00716 --(ci->numChildrenToDo);
00717 }
00718
00722 int icl_toWireString(ICLTerm* t, char** termAsString, size_t* termAsStringLen)
00723 {
00724 GByteArray* bytes = g_byte_array_new();
00725 GPtrArray* compoundList = g_ptr_array_new();
00726 GPtrArray* workingList = g_ptr_array_new();
00727 ICLTerm* currentTerm = NULL;
00728 compoundInfo_t* sentinel;
00729 compoundInfo_t* ci;
00730 compoundInfo_t* currentCompound;
00731 char startChar;
00732 char* separator;
00733 int childNum;
00734 guint8* tmpData;
00735 size_t tmpLen;
00736 int numberLen;
00737 int isCompound;
00738 int numArgs;
00739 char* functor;
00740 int zeroLenCompound = FALSE;
00741 int compoundSize = 0;
00742 int i;
00743 unsigned int ui;
00744
00745
00746
00747
00748
00749
00750
00751
00752
00753 g_ptr_array_add(workingList, t);
00754
00755 sentinel = compoundInfo_new();
00756 sentinel->numChildrenToDo = 1;
00757 sentinel->originalNumChildren = 1;
00758 g_ptr_array_add(compoundList, sentinel);
00759
00760 while((compoundList->len > 0) ||
00761 (workingList->len > 0)) {
00762 zeroLenCompound = FALSE;
00763 currentTerm = (ICLTerm*)g_ptr_array_index(workingList, workingList->len - 1);
00764 (void)g_ptr_array_remove_index(workingList, workingList->len - 1);
00765 currentCompound = (compoundInfo_t*)g_ptr_array_index(compoundList, compoundList->len - 1);
00766 childNum = compoundInfo_getCurrentChildNum(currentCompound);
00767 tmpData = compoundInfo_getPreChild(currentCompound, childNum, &tmpLen);
00768 if(tmpData != NULL) {
00769 g_byte_array_append(bytes, tmpData, tmpLen);
00770 }
00771 switch(currentTerm->iclType) {
00772 case icl_list_type:
00773 g_byte_array_append(bytes, (guint8*)"[", 1);
00774 numArgs = icl_NumTerms(currentTerm);
00775 ci = compoundInfo_new();
00776 compoundInfo_setPostPend(ci, (guint8*)"]", 1);
00777 compoundInfo_setNumChildren(ci, numArgs);
00778 compoundInfo_setPreAllButFirst(ci, (guint8*)",", 1);
00779 g_ptr_array_add(compoundList, ci);
00780 isCompound = TRUE;
00781 break;
00782 case icl_group_type:
00783 icl_GetGroupChars(currentTerm, &startChar, &separator);
00784 icl_stFree(separator);
00785 g_byte_array_append(bytes, (guint8*)&startChar, 1);
00786 numArgs = icl_NumTerms(currentTerm);
00787 ci = compoundInfo_new();
00788 switch(startChar) {
00789 case '{':
00790 compoundInfo_setPostPend(ci, (guint8*)"}", 1);
00791 default:
00792 compoundInfo_setPostPend(ci, (guint8*)")", 1);
00793 }
00794 compoundInfo_setNumChildren(ci, numArgs);
00795 compoundInfo_setPreAllButFirst(ci, (guint8*)",", 1);
00796 g_ptr_array_add(compoundList, ci);
00797 isCompound = TRUE;
00798 break;
00799 case icl_struct_type:
00800 functor = icl_Functor(currentTerm);
00801 numArgs = icl_NumTerms(currentTerm);
00802 ci = compoundInfo_new();
00803 g_byte_array_append(bytes, (guint8*)functor, strlen(functor));
00804 g_byte_array_append(bytes, (guint8*)"(", 1);
00805 compoundInfo_setPostPend(ci, (guint8*)")", 1);
00806 compoundInfo_setNumChildren(ci, numArgs);
00807 compoundInfo_setPreAllButFirst(ci, (guint8*)",", 1);
00808 g_ptr_array_add(compoundList, ci);
00809 isCompound = TRUE;
00810 break;
00811 case icl_int_type:
00812 case icl_float_type:
00813 case icl_str_type:
00814 case icl_var_type:
00815 case icl_dataq_type:
00816 isCompound = FALSE;
00817 numArgs = 0;
00818 break;
00819 default:
00820 fprintf(stderr, "libicl.c icl_toWireString() unknown type [%i] in term at %p\n", currentTerm->iclType, currentTerm);
00821 return FALSE;
00822 }
00823
00824 if(isCompound) {
00825 ICLTerm* toAdd;
00826
00827
00828
00829 if(numArgs > 0) {
00830 for(i = numArgs - 1; i >= 0; --i) {
00831 toAdd = icl_NthTerm(currentTerm, i + 1);
00832 g_ptr_array_add(workingList, toAdd);
00833
00834 {
00835 char* ds = icl_NewStringFromTerm(toAdd);
00836
00837 icl_stFree(ds);
00838 }
00839
00840 }
00841 continue;
00842 }
00843 else {
00844 zeroLenCompound = TRUE;
00845 }
00846 }
00847
00848 compoundSize = compoundList->len;
00849 currentCompound = (compoundInfo_t*)g_ptr_array_index(compoundList, compoundList->len - 1);
00850 if(!zeroLenCompound) {
00851 switch(currentTerm->iclType) {
00852 case icl_int_type:
00853 numberLen = snprintf(NULL, 0, get64BitFormat(), *((gint64*)currentTerm->p));
00854 if(numberLen < 0) {
00855 numberLen = 128;
00856 }
00857 tmpData = (guint8*)malloc(numberLen + 1);
00858 numberLen = snprintf((char*)tmpData, numberLen + 1, get64BitFormat(), *((gint64*)currentTerm->p));
00859 if(numberLen < 0) {
00860 numberLen = 128;
00861 }
00862 g_byte_array_append(bytes, tmpData, strlen((char*)tmpData));
00863
00864
00865
00866 free(tmpData);
00867 break;
00868 case icl_float_type:
00869 numberLen = snprintf(NULL, 0, "%f", *((double*)currentTerm->p));
00870 if(numberLen < 0) {
00871 numberLen = 128;
00872 }
00873 tmpData = (guint8*)malloc(numberLen + 1);
00874 numberLen = snprintf((char*)tmpData, numberLen + 1, "%f", *((double*)currentTerm->p));
00875 if(numberLen < 0) {
00876 numberLen = 128;
00877 }
00878 g_byte_array_append(bytes, tmpData, strlen((char*)tmpData));
00879
00880
00881
00882 free(tmpData);
00883 break;
00884 case icl_var_type:
00885 g_byte_array_append(bytes, (guint8*)currentTerm->p, strlen((char*)currentTerm->p));
00886
00887
00888
00889 break;
00890 case icl_str_type:
00891 if(currentTerm->needsQuotes == 1) {
00892 tmpData = (guint8*)icl_stQuoteForce((char*)currentTerm->p);
00893 }
00894 else {
00895 tmpData = (guint8*)currentTerm->p;
00896 }
00897 g_byte_array_append(bytes, tmpData, strlen((char*)tmpData));
00898
00899
00900
00901
00902
00903
00904 break;
00905 case icl_dataq_type:
00906 tmpData = (guint8*)currentTerm->p;
00907
00908 g_byte_array_append(bytes, (guint8*)"icldataq(\"", 10);
00909 for(ui = 0; ui < currentTerm->len; ++ui) {
00910 if(tmpData[ui] == '"') {
00911 g_byte_array_append(bytes, (guint8*)"\"\"", 2);
00912 }
00913 else {
00914 g_byte_array_append(bytes, &tmpData[ui], 1);
00915 }
00916 }
00917 g_byte_array_append(bytes, (guint8*)"\")", 2);
00918 break;
00919 default:
00920 fprintf(stderr, "libicl.c icl_toWireString() unknown non-compound type [%i] at %p\n", currentTerm->iclType, currentTerm);
00921 return FALSE;
00922 }
00923 tmpData = compoundInfo_getPostChild(currentCompound, compoundInfo_getCurrentChildNum(currentCompound), &tmpLen);
00924 if(tmpData != NULL) {
00925 g_byte_array_append(bytes, tmpData, tmpLen);
00926 }
00927 compoundInfo_childFinished(currentCompound);
00928
00929
00930
00931 }
00932 else {
00933
00934 }
00935
00936 while(compoundInfo_finished(currentCompound)) {
00937 tmpData = compoundInfo_getPostPend(currentCompound, &tmpLen);
00938 if(tmpData != NULL) {
00939 g_byte_array_append(bytes, tmpData, tmpLen);
00940
00941
00942
00943 }
00944 (void)g_ptr_array_remove_index(compoundList, compoundList->len - 1);
00945 free(currentCompound);
00946
00947
00948
00949 if(compoundList->len == 0) {
00950 #ifdef NORMAL_GC
00951 *termAsString = (char*)malloc(bytes->len);
00952 memcpy(*termAsString, bytes->data, bytes->len);
00953 *termAsStringLen = bytes->len;
00954 g_byte_array_free(bytes, FALSE);
00955 g_ptr_array_free(compoundList, TRUE);
00956 g_ptr_array_free(workingList, TRUE);
00957 #else
00958 *termAsString = (char*)bytes->data;
00959 *termAsStringLen = bytes->len;
00960 g_byte_array_free(bytes, FALSE);
00961 g_ptr_array_free(compoundList, TRUE);
00962 g_ptr_array_free(workingList, TRUE);
00963 #endif
00964 return TRUE;
00965 }
00966 currentCompound = (compoundInfo_t*)g_ptr_array_index(compoundList, compoundList->len - 1);
00967 tmpData = compoundInfo_getPostChild(currentCompound, compoundInfo_getCurrentChildNum(currentCompound), &tmpLen);
00968 if(tmpData != NULL) {
00969 g_byte_array_append(bytes, tmpData, tmpLen);
00970 }
00971 compoundInfo_childFinished(currentCompound);
00972
00973
00974
00975 }
00976 }
00977 fprintf(stderr, "libicl.c icl_toWireString() This should never be reached\n");
00978 g_byte_array_free(bytes, TRUE);
00979 g_ptr_array_free(compoundList, TRUE);
00980 g_ptr_array_free(workingList, TRUE);
00981 return FALSE;
00982 }
00983
00991 EXPORT_MSCPP
00992 ICLTerm* EXPORT_BORLAND
00993 icl_NewTermFromData(char* data, size_t len)
00994 {
00995 ICLTerm* res = parser_getTermFromString(data, len);
00996 CHECK_LEAKS();
00997 return res;
00998 }
00999
01007 EXPORT_MSCPP
01008 ICLTerm * EXPORT_BORLAND
01009 icl_NewTermFromString(char* t)
01010 {
01011 ICLTerm* res = NULL;
01012 if(t != NULL) {
01013 res = icl_NewTermFromData(t, strlen(t));
01014 CHECK_LEAKS();
01015 return res;
01016 }
01017 else {
01018 return NULL;
01019 }
01020 }
01021
01022
01028 EXPORT_MSCPP
01029 char * EXPORT_BORLAND
01030 icl_NewStringFromTerm(ICLTerm const*t)
01031 {
01032 char *res = NULL;
01033 char* tmp = NULL;
01034 int tmpBufSz = 0;
01035
01036
01037 if (t==NULL)
01038 return NULL;
01039
01040
01041 if (!icl_IsValid(t))
01042 return NULL;
01043
01044 if (icl_IsVar(t)) {
01045 res = strdup(t->p);
01046 }
01047 else if (icl_IsInt(t)) {
01048 tmpBufSz = snprintf(tmp, 0, get64BitFormat(), icl_Int(t));
01049 if(tmpBufSz < 0) {
01050 tmpBufSz = 128;
01051 }
01052 ++tmpBufSz;
01053 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01054 (void)memset(tmp, 0, tmpBufSz);
01055 snprintf(tmp, tmpBufSz, get64BitFormat(), icl_Int(t));
01056 res = tmp;
01057 }
01058 else if (icl_IsFloat(t)) {
01059 tmpBufSz = snprintf(tmp, 0, "%f", icl_Float(t));
01060 if(tmpBufSz < 0) {
01061 tmpBufSz = 128;
01062 }
01063 ++tmpBufSz;
01064 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01065 (void)memset(tmp, 0, tmpBufSz);
01066 snprintf(tmp, tmpBufSz, "%f", icl_Float(t));
01067 res = tmp;
01068 }
01069 else if (icl_IsStr(t)) {
01070 if(t->needsQuotes == 1) {
01071 res = strdup(icl_stQuoteForce(t->p));
01072 }
01073 else {
01074 res = strdup(t->p);
01075 }
01076 }
01077 else if(icl_IsDataQ(t)) {
01078
01079 res = (char*)malloc(icl_Len(t) + 1);
01080 res = memcpy(res, icl_DataQ(t), icl_Len(t));
01081 res[icl_Len(t)] = '\0';
01082 }
01083 else if (icl_IsStruct(t)) {
01084 int first = TRUE;
01085 ICLListType *args;
01086
01087
01088 if (icl_stIsOperator(icl_Functor(t))>0) {
01089 args = icl_Arguments(t);
01090
01091 icl_stAppend(&res, icl_NewStringFromTerm(args->elt));
01092
01093 icl_stAppend(&res, icl_Functor(t));
01094
01095 args = args->next;
01096 if (args) {
01097 icl_stAppend(&res, icl_NewStringFromTerm(args->elt));
01098 }
01099 }
01100 else {
01101 res = strdup(icl_Functor(t));
01102 args = icl_Arguments(t);
01103 icl_stAppend(&res, "(");
01104 while (args) {
01105 char *arg;
01106 arg = icl_NewStringFromTerm(args->elt);
01107 if (first) {
01108 first = FALSE;
01109 }
01110 else {
01111 icl_stAppend(&res, ",");
01112 }
01113 icl_stAppend(&res, arg);
01114 icl_stFree(arg);
01115 args = args->next;
01116 }
01117 icl_stAppend(&res, ")");
01118 }
01119 }
01120 else if (icl_IsList(t)) {
01121 int first = TRUE;
01122 ICLListType *args;
01123 args = icl_List(t);
01124 res = strdup("[");
01125 while (args) {
01126 char *arg;
01127 arg = icl_NewStringFromTerm(args->elt);
01128 if (first)
01129 first = FALSE;
01130 else icl_stAppend(&res, ",");
01131 icl_stAppend(&res, arg);
01132 icl_stFree(arg);
01133 args = args->next;
01134 }
01135 icl_stAppend(&res, "]");
01136 }
01137 else if (icl_IsGroup(t)) {
01138 int first = TRUE;
01139 ICLListType *args;
01140 char start;
01141 char *separator;
01142
01143 icl_GetGroupChars(t, &start, &separator);
01144 args = icl_List(t);
01145 res = strdup("[");
01146 res[0] = start;
01147 while (args) {
01148 char *arg;
01149 arg = icl_NewStringFromTerm(args->elt);
01150 if (first)
01151 first = FALSE;
01152 else icl_stAppend(&res, separator);
01153 icl_stAppend(&res, arg);
01154 icl_stFree(arg);
01155 args = args->next;
01156 }
01157 icl_stAppend(&res, "]");
01158 if (start == '(')
01159 res[strlen(res)-1] = start + 1;
01160 else
01161 res[strlen(res)-1] = start + 2;
01162
01163 icl_stFree(separator);
01164 }
01165 else {
01166 fprintf(stderr, "Unknown term type for icl_NewStringFromTerm: %i\n", t->iclType);
01167 }
01168
01169 return (res);
01170 }
01171
01172 EXPORT_MSCPP
01173 char* EXPORT_BORLAND
01174 icl_UnquotedStringFromStr(ICLTerm* t)
01175 {
01176 if(!icl_IsStr(t)) {
01177 return NULL;
01178 }
01179
01180 return strdup(t->p);
01181 }
01182
01183 EXPORT_MSCPP
01184 char* EXPORT_BORLAND
01185 icl_ForcedQuotedStringFromStr(ICLTerm* t)
01186 {
01187 if(!icl_IsStr(t)) {
01188 return NULL;
01189 }
01190
01191 return strdup(icl_stQuoteForce(t->p));
01192 }
01193
01194 EXPORT_MSCPP
01195 char* EXPORT_BORLAND
01196 icl_MinimallyQuotedStringFromStr(ICLTerm* t)
01197 {
01198 if(!icl_IsStr(t)) {
01199 return NULL;
01200 }
01201
01202 return icl_NewStringFromTerm(t);
01203 }
01204
01205
01206
01207
01208
01209
01210 EXPORT_MSCPP
01211 char * EXPORT_BORLAND
01212 pt(ICLTerm *t)
01213 {
01214 return icl_NewStringFromTerm(t);
01215 }
01216
01223 EXPORT_MSCPP
01224 char * EXPORT_BORLAND
01225 icl_NewStringStructFromTerm(ICLTerm *t)
01226 {
01227 char* INT64FORMAT = get64BitFormatWrapped("int(", ")");
01228 int tmpBufSz = 0;
01229 char *res = NULL;
01230 char* tmp = NULL;
01231
01232
01233 if (!icl_IsValid(t)) {
01234 free(INT64FORMAT);
01235 return NULL;
01236 }
01237
01238 if (icl_IsVar(t)) {
01239 tmpBufSz = snprintf(tmp, 0, "var(%s)", (char*)(t->p));
01240 ++tmpBufSz;
01241 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01242 memset(tmp, 0, tmpBufSz);
01243 snprintf(tmp, tmpBufSz, "var(%s)", (char*)(t->p));
01244 res = tmp;
01245 }
01246 else if (icl_IsInt(t)) {
01247 tmpBufSz = snprintf(tmp, 0, INT64FORMAT, icl_Int(t));
01248 ++tmpBufSz;
01249 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01250 memset(tmp, 0, tmpBufSz);
01251 snprintf(tmp, tmpBufSz, INT64FORMAT, icl_Int(t));
01252 res = tmp;
01253 }
01254 else if (icl_IsFloat(t)) {
01255 tmpBufSz = snprintf(tmp, 0, "float(%f)", icl_Float(t));
01256 ++tmpBufSz;
01257 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01258 memset(tmp, 0, tmpBufSz);
01259 snprintf(tmp, tmpBufSz, "float(%f)", icl_Float(t));
01260 res = tmp;
01261 }
01262 else if (icl_IsStr(t)) {
01263 tmpBufSz = snprintf(tmp, 0, "str(%s)", icl_stQuote(t->p));
01264 ++tmpBufSz;
01265 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01266 memset(tmp, 0, tmpBufSz);
01267 snprintf(tmp, tmpBufSz, "str(%s)", icl_stQuote(t->p));
01268 res = tmp;
01269 }
01270 else if (icl_IsStruct(t)) {
01271 int first = TRUE;
01272 ICLListType *args;
01273 tmpBufSz = snprintf(tmp, 0, "struct(%s,", icl_Functor(t));
01274 ++tmpBufSz;
01275 tmp = (char*)malloc(tmpBufSz * sizeof(char));
01276 memset(tmp, 0, tmpBufSz);
01277 snprintf(tmp, tmpBufSz, "struct(%s,", icl_Functor(t));
01278 res = tmp;
01279 args = icl_Arguments(t);
01280 icl_stAppend(&res, "(");
01281 while (args) {
01282 char *arg;
01283 arg = icl_NewStringStructFromTerm(args->elt);
01284 if (first) {
01285 first = FALSE;
01286 }
01287 else {
01288 icl_stAppend(&res, ",");
01289 }
01290 icl_stAppend(&res, arg);
01291 icl_stFree(arg);
01292 args = args->next;
01293 }
01294 icl_stAppend(&res, ")");
01295 }
01296 else if (icl_IsList(t)) {
01297 int first = TRUE;
01298 ICLListType *args;
01299 args = icl_List(t);
01300 res = strdup("list([");
01301 while (args) {
01302 char *arg;
01303 arg = icl_NewStringStructFromTerm(args->elt);
01304 if (first) {
01305 first = FALSE;
01306 }
01307 else {
01308 icl_stAppend(&res, ",");
01309 }
01310 icl_stAppend(&res, arg);
01311 icl_stFree(arg);
01312 args = args->next;
01313 }
01314 icl_stAppend(&res, "])");
01315 }
01316 else if (icl_IsGroup(t)) {
01317 int first = TRUE;
01318 ICLListType *args;
01319 char start;
01320 char *separator;
01321
01322 icl_GetGroupChars(t, &start, &separator);
01323 args = icl_List(t);
01324 res = strdup("group([");
01325 while (args) {
01326 char *arg;
01327 arg = icl_NewStringStructFromTerm(args->elt);
01328 if (first) {
01329 first = FALSE;
01330 }
01331 else {
01332 icl_stAppend(&res, separator);
01333 }
01334 icl_stAppend(&res, arg);
01335 icl_stFree(arg);
01336 args = args->next;
01337 }
01338 icl_stAppend(&res, "])");
01339 if (start == '(') {
01340 res[strlen(res)-1] = start + 1;
01341 }
01342 else {
01343 res[strlen(res)-1] = start + 2;
01344 }
01345
01346 icl_stFree(separator);
01347 }
01348 free(INT64FORMAT);
01349 return (res);
01350 }
01351
01352 enum CompoundType {
01353 compound_sentinel_type,
01354 compound_struct_type,
01355 compound_list_type,
01356 compound_group_type
01357 }
01358 ;
01359
01360 struct CompoundInfo
01361 {
01362 enum CompoundType cType;
01363 void* p;
01364 int numArgsExpected;
01365 }
01366 ;
01367
01368 struct CompoundStructType
01369 {
01370 char* functor;
01371 ICLListType* args;
01372 }
01373 ;
01374
01375 struct CompoundListType
01376 {
01377 ICLListType* args;
01378 }
01379 ;
01380
01381 struct CompoundGroupType
01382 {
01383 char startC;
01384 char* sep;
01385 ICLListType* args;
01386 }
01387 ;
01388
01389 struct CompoundSentinelType
01390 {
01391 ICLTerm* term;
01392 }
01393 ;
01394
01395 static void icl_add_compound_argument(struct CompoundInfo* ci, ICLTerm* t)
01396 {
01397 struct CompoundStructType* structCompound;
01398 struct CompoundListType* listCompound;
01399 struct CompoundGroupType* groupCompound;
01400
01401 switch(ci->cType) {
01402 case compound_struct_type:
01403 structCompound = (struct CompoundStructType*)ci->p;
01404 if(!structCompound->args) {
01405 structCompound->args = icl_NewCons(t, NULL);
01406 }
01407 else {
01408 structCompound->args = icl_NewCons(t, structCompound->args);
01409 }
01410 ci->numArgsExpected--;
01411 break;
01412 case compound_list_type:
01413 listCompound = (struct CompoundListType*)ci->p;
01414 if(!listCompound->args) {
01415 listCompound->args = icl_NewCons(t, NULL);
01416 }
01417 else {
01418 listCompound->args = icl_NewCons(t, listCompound->args);
01419 }
01420 ci->numArgsExpected--;
01421 break;
01422 case compound_group_type:
01423 groupCompound = (struct CompoundGroupType*)ci->p;
01424 if(!groupCompound->args) {
01425 groupCompound->args = icl_NewCons(t, NULL);
01426 }
01427 else {
01428 groupCompound->args = icl_NewCons(t, groupCompound->args);
01429 }
01430 ci->numArgsExpected--;
01431 break;
01432 case compound_sentinel_type:
01433 ((struct CompoundSentinelType*)ci->p)->term = t;
01434 ci->numArgsExpected--;
01435 break;
01436 default:
01437 fprintf(stderr, "Unknown compound type\n");
01438 break;
01439 }
01440 if(ci->numArgsExpected < 0) {
01441 fprintf(stderr, "numArgsExpected < 0\n");
01442 }
01443 }
01444
01449 EXPORT_MSCPP
01450 ICLTerm *EXPORT_BORLAND
01451 icl_copy_term_nonrec(ICLTerm const* t, struct dyn_array* vars)
01452 {
01453 struct const_dyn_array termStack;
01454 struct dyn_array compoundStack;
01455 ICLTerm* currTerm = NULL;
01456 struct CompoundInfo* currCompound;
01457 struct CompoundStructType* structCompound;
01458 struct CompoundListType* listCompound;
01459 struct CompoundGroupType* groupCompound;
01460 struct CompoundSentinelType sentinelCompound;
01461 struct CompoundInfo sentinelCI;
01462
01463 if(t == NULL) {
01464 return NULL;
01465 }
01466
01467 icl_init_const_dyn_array(&termStack);
01468 icl_append_const_dyn_array(&termStack, t);
01469 icl_init_dyn_array(&compoundStack);
01470 sentinelCI.p = &sentinelCompound;
01471 sentinelCI.cType = compound_sentinel_type;
01472 sentinelCI.numArgsExpected = 1;
01473 icl_append_dyn_array(&compoundStack, &sentinelCI);
01474 if(termStack.count == 0) {
01475 fprintf(stderr, "icl_copy_term_nonrec termStack count is 0!\n");
01476 }
01477 while(termStack.count != 0) {
01478 currTerm = (ICLTerm*)termStack.item[termStack.count - 1];
01479 termStack.item[termStack.count - 1] = NULL;
01480 termStack.count--;
01481 if(vars) {
01482 icl_deref(&currTerm, *vars);
01483 }
01484
01485 if(icl_IsVar(currTerm)) {
01486 currTerm = icl_NewVar(icl_Str(currTerm));
01487 }
01488 else if(icl_IsInt(currTerm)) {
01489 currTerm = icl_NewInt(icl_Int(currTerm));
01490 }
01491 else if(icl_IsFloat(currTerm)) {
01492 currTerm = icl_NewFloat(icl_Float(currTerm));
01493 }
01494 else if(icl_IsStr(currTerm)) {
01495 currTerm = icl_NewStr(icl_Str(currTerm));
01496 }
01497 else if(icl_IsDataQ(currTerm)) {
01498 currTerm = icl_NewDataQ(icl_DataQ(currTerm), icl_Len(currTerm));
01499 }
01500 else if(icl_IsStruct(currTerm)) {
01501
01502
01503
01504
01505
01506 struct CompoundInfo* ci = (struct CompoundInfo*)malloc(sizeof(struct CompoundInfo)) ;
01507 struct CompoundStructType* c = (struct CompoundStructType*)malloc(sizeof(struct CompoundStructType));
01508 ICLListType* args = icl_Arguments(currTerm);
01509 ci->p = c;
01510 ci->cType = compound_struct_type;
01511 ci->numArgsExpected = 0;
01512 c->functor = icl_Functor(currTerm);
01513 c->args = NULL;
01514 while(args) {
01515 ci->numArgsExpected++;
01516 icl_append_const_dyn_array(&termStack, args->elt);
01517 args = args->next;
01518 }
01519 icl_append_dyn_array(&compoundStack, ci);
01520 if(ci->numArgsExpected > 0) {
01521 continue;
01522 }
01523 }
01524 else if(icl_IsList(currTerm)) {
01525 struct CompoundInfo* ci = (struct CompoundInfo*)malloc(sizeof(struct CompoundInfo));
01526 struct CompoundListType* c = (struct CompoundListType*)malloc(sizeof(struct CompoundListType));
01527 ICLListType* args = icl_List(currTerm);
01528 ci->p = c;
01529 ci->cType = compound_list_type;
01530 ci->numArgsExpected = 0;
01531 c->args = NULL;
01532 while(args) {
01533 ci->numArgsExpected++;
01534 icl_append_const_dyn_array(&termStack, args->elt);
01535 args = args->next;
01536 }
01537 icl_append_dyn_array(&compoundStack, ci);
01538 if(ci->numArgsExpected > 0) {
01539 continue;
01540 }
01541 }
01542 else if(icl_IsGroup(currTerm)) {
01543 struct CompoundInfo* ci = (struct CompoundInfo*)malloc(sizeof(struct CompoundInfo));
01544 struct CompoundGroupType* c = (struct CompoundGroupType*)malloc(sizeof(struct CompoundGroupType));
01545 ICLListType* args = icl_List(currTerm);
01546 ci->p = c;
01547 ci->cType = compound_group_type;
01548 ci->numArgsExpected = 0;
01549 c->args = NULL;
01550 icl_GetGroupChars(currTerm, &(c->startC), &(c->sep));
01551 while(args) {
01552 ci->numArgsExpected++;
01553 icl_append_const_dyn_array(&termStack, args->elt);
01554 args = args->next;
01555 }
01556 icl_append_dyn_array(&compoundStack, ci);
01557 if(ci->numArgsExpected > 0) {
01558 continue;
01559 }
01560 }
01561 else if(currTerm == NULL) {
01562 currTerm = NULL;
01563 }
01564 else {
01565 char* s = icl_NewStringFromTerm(t);
01566 fprintf(stderr, "Unknown type in icl_copy_term_nonrec: [%s]\n", s);
01567 icl_stFree(s);
01568 currTerm = NULL;
01569 }
01570
01571
01572
01573
01574
01575 currCompound = (struct CompoundInfo*)compoundStack.item[compoundStack.count - 1];
01576
01577 if(currCompound->numArgsExpected > 0) {
01578 icl_add_compound_argument(currCompound, currTerm);
01579 }
01580
01581 while(currCompound->numArgsExpected == 0) {
01582 switch(currCompound->cType) {
01583 case compound_struct_type:
01584 structCompound = (struct CompoundStructType*)currCompound->p;
01585 currTerm = icl_NewStructFromList(structCompound->functor, icl_NewList(structCompound->args));
01586 free(structCompound);
01587 free(currCompound);
01588 structCompound = NULL;
01589 currCompound = NULL;
01590 break;
01591 case compound_list_type:
01592 listCompound = (struct CompoundListType*)currCompound->p;
01593 currTerm = icl_NewList(listCompound->args);
01594 free(listCompound);
01595 free(currCompound);
01596 listCompound = NULL;
01597 currCompound = NULL;
01598 break;
01599 case compound_group_type:
01600 groupCompound = (struct CompoundGroupType*)currCompound->p;
01601 currTerm = icl_NewGroup(groupCompound->startC, groupCompound->sep, groupCompound->args);
01602 free(groupCompound);
01603 free(currCompound);
01604 groupCompound = NULL;
01605 currCompound = NULL;
01606 break;
01607 case compound_sentinel_type:
01608 if(compoundStack.count != 1) {
01609 fprintf(stderr, "icl_copy_term_nonrec got sentinel but nonempty compoundStack\n");
01610 }
01611 if(compoundStack.item != NULL) {
01612 free(compoundStack.item);
01613 }
01614 if(termStack.item != NULL) {
01615 free(termStack.item);
01616 }
01617 CHECK_LEAKS();
01618 return ((struct CompoundSentinelType*)(currCompound->p))->term;
01619 break;
01620 default:
01621 fprintf(stderr, "icl_copy_term_nonrec got unknown compound type\n");
01622 if(compoundStack.item != NULL) {
01623 free(compoundStack.item);
01624 }
01625 return NULL;
01626 break;
01627 }
01628 compoundStack.item[compoundStack.count - 1] = NULL;
01629 compoundStack.count--;
01630 currCompound = (struct CompoundInfo*)compoundStack.item[compoundStack.count - 1];
01631 icl_add_compound_argument(currCompound, currTerm);
01632 }
01633 }
01634 icl_WriteTerm(currTerm);
01635 printf("\n");
01636 fprintf(stderr, "icl_copy_term_nonrec unreachable\n");
01637 return NULL;
01638 }
01639
01640
01641
01642
01643
01644
01645
01646
01647
01648
01649
01650
01651
01652
01653
01654
01655
01656
01657
01658
01659
01660
01661
01662
01663
01664
01665
01666
01667
01668
01669
01670
01671
01672
01673
01674
01675
01676
01677
01678
01679
01680
01681
01682
01683
01684
01685
01686
01687
01688
01689
01690
01691
01695 static
01696 ICLListType *
01697 icl_copy_list_type(ICLListType *list, struct dyn_array *vars)
01698 {
01699 ICLListType *res = NULL, *end = NULL;
01700
01701 while (list) {
01702 if (!res) {
01703 ICLTerm* copy = icl_copy_term_nonrec(list->elt, vars);
01704 res = icl_NewCons(copy, NULL);
01705 end = res;
01706 }
01707 else {
01708 end->next = icl_NewCons(icl_copy_term_nonrec(list->elt, vars), NULL);
01709 end = end->next;
01710 }
01711 list = list->next;
01712 }
01713
01714 return(res);
01715 }
01716
01717
01718
01722 EXPORT_MSCPP
01723 ICLTerm * EXPORT_BORLAND
01724 icl_CopyTerm(ICLTerm const*t)
01725 {
01726 return (icl_copy_term(t, NULL));
01727 }
01728
01729
01733 EXPORT_MSCPP
01734 ICLListType * EXPORT_BORLAND
01735 icl_CopyListType(ICLListType *list)
01736 {
01737 return(icl_copy_list_type(list, NULL));
01738 }
01739
01740
01741
01747 EXPORT_MSCPP
01748 ICLTerm * EXPORT_BORLAND
01749 icl_NewInt(gint64 i)
01750 {
01751 ICLTerm *res = malloc(sizeof(ICLTerm));
01752 gint64 *iptr = malloc(sizeof(gint64));
01753
01754 *iptr = i;
01755 res->iclType = icl_int_type;
01756 res->p = iptr;
01757 res->magic_cookie = ICL_MAGIC_COOKIE;
01758 res->len = sizeof(gint64);
01759
01760 res->refCount = 1;
01761 res->glibAlloc = 0;
01762 res->needsQuotes = 0;
01763 return (res);
01764 }
01765
01766
01772 EXPORT_MSCPP
01773 ICLTerm * EXPORT_BORLAND
01774 icl_NewFloat(double f)
01775 {
01776 ICLTerm *res = malloc(sizeof(ICLTerm));
01777 double *fptr = malloc(sizeof(double));
01778
01779 *fptr = f;
01780 res->iclType = icl_float_type;
01781 res->p = fptr;
01782 res->magic_cookie = ICL_MAGIC_COOKIE;
01783 res->len = sizeof(double);
01784
01785 res->refCount = 1;
01786 res->glibAlloc = 0;
01787 res->needsQuotes = 0;
01788 return (res);
01789 }
01790
01797 static char* trimAndStrdup(char const* s)
01798 {
01799 char const* start;
01800 char const* end;
01801 char* result;
01802 for(start = s; (*start != '\0') && (!isgraph(*start) || isspace(*start)); ++start);
01803 for(end = s + strlen(s) - 1; (end != start) && (!isgraph(*end) || isspace(*end)); --end);
01804
01805 result = (char*)malloc(end - start + 1 + 1);
01806 memcpy(result, start, end - start + 1);
01807 result[end - start + 1] = '\0';
01808 return result;
01809 }
01810
01815 static char* trimInPlace(char* s)
01816 {
01817 char* start;
01818 char* end;
01819 for(start = s; (*start != '\0') && (!isgraph(*start) || isspace(*start)); ++start);
01820 for(end = s + strlen(s) - 1; (end != start) && (!isgraph(*end) || isspace(*end)); --end);
01821
01822 memmove(s, start, (end - start + 1));
01823 s[end - start + 1] = '\0';
01824
01825 return s;
01826 }
01827
01831 EXPORT_MSCPP
01832 int EXPORT_BORLAND
01833 icl_stIsProperlyQuoted(char* s)
01834 {
01835 int quotesAllowed = 0;
01836 int originalLen = strlen(s);
01837 int i;
01838
01839 if(*s == '\'') {
01840 if((originalLen > 1) && *(s + originalLen - 1) == '\'') {
01841 quotesAllowed = 1;
01842 }
01843 else {
01844 return FALSE;
01845 }
01846 }
01847
01848 for(i = 1; i < originalLen - 1; ++i) {
01849 if(s[i] == '\'') {
01850 if(!quotesAllowed) {
01851 return FALSE;
01852 }
01853 if(((i + 1) < originalLen - 1) && (s[i + 1] == '\'')) {
01854 ++i;
01855 continue;
01856 }
01857 else {
01858 return FALSE;
01859 }
01860 }
01861 }
01862
01863 return TRUE;
01864 }
01865
01866 static char* unquoteHelper(char const* from, char* to)
01867 {
01868 size_t index;
01869 int negativeOffset;
01870 size_t len = strlen(from);
01871
01872 if((--len > 0) && (from[0] == '\'')) {
01873
01874 for(index = 1, negativeOffset = 1;
01875 index < len;
01876 ++index) {
01877 to[index - negativeOffset] = from[index];
01878 if(from[index] == '\'') {
01879
01880 ++index;
01881 ++negativeOffset;
01882 }
01883 }
01884 to[len - negativeOffset] = '\0';
01885 }
01886
01887 return to;
01888 }
01889
01904 static char* unquoteInPlace(char* s)
01905 {
01906 return unquoteHelper(s, s);
01907 }
01908
01912 void icl_setStrFromProperlyQuoted(char* s, ICLTerm* res)
01913 {
01914 s = unquoteInPlace(s);
01915
01916 if(s[0] != '\0') {
01917 ICLTerm* term = icl_NewTermFromString(s);
01918 res->p = s;
01919 if(!term) {
01920 res->needsQuotes = TRUE;
01921 }
01922 else if(!icl_IsStr(term)) {
01923 res->needsQuotes = TRUE;
01924 }
01925 else {
01926 res->needsQuotes = FALSE;
01927 }
01928 icl_Free(term);
01929 }
01930 else {
01931 res->p = s;
01932 res->needsQuotes = FALSE;
01933 }
01934 }
01935
01939 static void setIclStrValueFromString(char* s, ICLTerm* res)
01940 {
01941 if(icl_stIsProperlyQuoted(s)) {
01942 icl_setStrFromProperlyQuoted(s, res);
01943 }
01944 else {
01945 res->needsQuotes = TRUE;
01946 res->p = s;
01947 }
01948 res->len = strlen(res->p);
01949 }
01950
01956 EXPORT_MSCPP
01957 ICLTerm * EXPORT_BORLAND
01958 icl_NewStr(char const*s)
01959 {
01960 ICLTerm *res = NULL;
01961 char* stringCopy;
01962
01963 if(s) {
01964 res = malloc(sizeof(ICLTerm));
01965 stringCopy = trimAndStrdup(s);
01966
01967 res->iclType = icl_str_type;
01968 res->magic_cookie = ICL_MAGIC_COOKIE;
01969 res->refCount = 1;
01970 res->glibAlloc = 0;
01971
01972 setIclStrValueFromString(stringCopy, res);
01973 }
01974
01975 return (res);
01976 }
01977
01983 ICLTerm*
01984 icl_NewStrNoCopy(char *s)
01985 {
01986 ICLTerm *res = NULL;
01987
01988 if (s) {
01989 res = malloc(sizeof(ICLTerm));
01990 s = trimInPlace(s);
01991
01992 res->iclType = icl_str_type;
01993 res->magic_cookie = ICL_MAGIC_COOKIE;
01994 res->refCount = 1;
01995 res->glibAlloc = 0;
01996
01997 setIclStrValueFromString(s, res);
01998 res->len = strlen(s);
01999 }
02000
02001 return (res);
02002 }
02003
02009 EXPORT_MSCPP
02010 ICLTerm * EXPORT_BORLAND
02011 icl_NewVar(char *name)
02012 {
02013 ICLTerm *res = NULL;
02014
02015 if (name && *name) {
02016 res = malloc(sizeof(ICLTerm));
02017
02018 res->iclType = icl_var_type;
02019 res->p = strdup(name);
02020 res->magic_cookie = ICL_MAGIC_COOKIE;
02021 res->refCount = 1;
02022 res->glibAlloc = 0;
02023 res->needsQuotes = 0;
02024 res->len = strlen(name);
02025 }
02026
02027 return (res);
02028 }
02029
02030 ICLTerm *
02031 icl_NewVarNoCopy(char *name)
02032 {
02033 ICLTerm *res = NULL;
02034
02035 if (name && *name) {
02036 res = malloc(sizeof(ICLTerm));
02037
02038 res->iclType = icl_var_type;
02039 res->p = name;
02040 res->magic_cookie = ICL_MAGIC_COOKIE;
02041 res->refCount = 1;
02042 res->glibAlloc = 0;
02043 res->needsQuotes = 0;
02044 res->len = strlen(name);
02045 }
02046
02047 return (res);
02048 }
02049
02057 EXPORT_MSCPP
02058 ICLTerm * EXPORT_BORLAND
02059 icl_NewStructFromList(char const* functor, ICLTerm *args)
02060 {
02061 ICLTerm *res = NULL;
02062 ICLStructType *st = NULL;
02063 ICLTerm* functorAsTerm = NULL;
02064
02065
02066
02067 functorAsTerm = icl_NewStr(functor);
02068
02069 if (icl_IsList(args) && functorAsTerm) {
02070
02071 res = malloc(sizeof(ICLTerm));
02072 st = malloc(sizeof(ICLStructType));
02073
02074 st->numArgs = icl_NumTerms(args);
02075 st->args = args;
02076 st->functor = functorAsTerm;
02077
02078 res->iclType = icl_struct_type;
02079 res->p = st;
02080 res->magic_cookie = ICL_MAGIC_COOKIE;
02081 res->refCount = 1;
02082 res->glibAlloc = 0;
02083 res->needsQuotes = 0;
02084 res->len = sizeof(st);
02085 }
02086
02087 return (res);
02088 }
02089
02090
02091
02099 EXPORT_MSCPP
02100 ICLTerm * EXPORT_BORLAND
02101 icl_NewStruct(char const* functor, int arity, ...)
02102 {
02103 ICLTerm *arg, *res = NULL;
02104
02105 va_list ap;
02106 int i=0;
02107
02108 ICLTerm* functorAsTerm = icl_NewStr(functor);
02109
02110
02111
02112 if (functorAsTerm) {
02113 ICLStructType *st = malloc(sizeof(ICLStructType));
02114 ICLTerm *args;
02115
02116 res = malloc(sizeof(ICLTerm));
02117
02118 args = icl_NewList(NULL);
02119
02120
02121 va_start(ap, arity);
02122 for (i=0; i< arity;i++) {
02123 arg = va_arg(ap, ICLTerm*);
02124 if (arg) {
02125 icl_AddToList(args, arg, TRUE);
02126 }
02127 }
02128 va_end(ap);
02129
02130 st->numArgs = arity;
02131 st->args = args;
02132 st->functor = functorAsTerm;
02133
02134 res->iclType = icl_struct_type;
02135 res->p = st;
02136 res->magic_cookie = ICL_MAGIC_COOKIE;
02137 res->refCount = 1;
02138 res->glibAlloc = 0;
02139 res->needsQuotes = 0;
02140 res->len = sizeof(st);
02141 }
02142
02143 return (res);
02144 }
02145
02146
02150 EXPORT_MSCPP
02151 ICLListType * EXPORT_BORLAND
02152 icl_NewCons(ICLTerm *elt, ICLListType *tail)
02153 {
02154 ICLListType *res = malloc(sizeof(ICLListType));
02155
02156 res->elt = elt;
02157 res->next = tail;
02158 if(elt != NULL) {
02159 iclIncRef(elt);
02160 }
02161
02162 return (res);
02163 }
02164
02165 EXPORT_MSCPP
02166 ICLTerm* EXPORT_BORLAND
02167 icl_NewDataQ(void const* data, size_t dataLen)
02168 {
02169 ICLTerm* res = malloc(sizeof(ICLTerm));
02170 res->p = malloc(dataLen);
02171 if(dataLen > 0) {
02172 memcpy(res->p, data, dataLen);
02173 }
02174 else {
02175 res->p = NULL;
02176 }
02177 res->len = dataLen;
02178 res->iclType = icl_dataq_type;
02179 res->magic_cookie = ICL_MAGIC_COOKIE;
02180 res->refCount = 1;
02181 res->glibAlloc = 0;
02182 res->needsQuotes = 0;
02183
02184 return res;
02185 }
02186
02187 ICLTerm*
02188 icl_NewDataQNoCopy(void* data, size_t dataLen)
02189 {
02190 ICLTerm* res = malloc(sizeof(ICLTerm));
02191 res->p = data;
02192 res->len = dataLen;
02193 res->iclType = icl_dataq_type;
02194 res->magic_cookie = ICL_MAGIC_COOKIE;
02195 res->refCount = 1;
02196 res->glibAlloc = 0;
02197 res->needsQuotes = 0;
02198
02199 return res;
02200 }
02201
02210 EXPORT_MSCPP
02211 ICLTerm * EXPORT_BORLAND
02212 icl_NewGroup(char startC, char *separator, ICLListType *list)
02213 {
02214 ICLTerm *res = malloc(sizeof(ICLTerm));
02215 ICLGroupType *gp = malloc(sizeof(ICLGroupType));
02216
02217 res->iclType = icl_group_type;
02218 gp->startChar = startC;
02219 gp->separator = strdup(separator);
02220 gp->list = list;
02221 res->p = gp;
02222 res->magic_cookie = ICL_MAGIC_COOKIE;
02223 res->refCount = 1;
02224 res->glibAlloc = 0;
02225 res->needsQuotes = 0;
02226 res->len = sizeof(gp);
02227
02228 return (res);
02229 }
02230
02237 EXPORT_MSCPP
02238 ICLTerm * EXPORT_BORLAND
02239 icl_NewList(ICLListType *list)
02240 {
02241 ICLTerm *res = malloc(sizeof(ICLTerm));
02242
02243 res->iclType = icl_list_type;
02244 res->p = list;
02245 res->magic_cookie = ICL_MAGIC_COOKIE;
02246 res->refCount = 1;
02247 res->glibAlloc = 0;
02248 res->needsQuotes = 0;
02249 res->len = sizeof(list);
02250
02251 return (res);
02252 }
02253
02254
02255 EXPORT_MSCPP
02256 void EXPORT_BORLAND
02257 icl_FreeTermSingle(ICLTerm *elt)
02258 {
02259
02260 icl_FreeTermMulti(elt,0,0);
02261 }
02262
02263 EXPORT_MSCPP
02264 void EXPORT_BORLAND
02265 icl_FreeTerm(ICLTerm *elt)
02266 {
02267 icl_FreeTermMulti(elt,0,0);
02268 }
02269
02282 EXPORT_MSCPP
02283 void EXPORT_BORLAND
02284 icl_stFree(void *p) {
02285 if (p) {
02286 #ifdef NORMAL_GC
02287 GC_debug_free(p); p = 0;
02288 #else
02289 free(p); p = 0;
02290 #endif
02291 }
02292 }
02293
02294
02295
02296
02297
02298
02299 static void
02300 icl_FreeTermMulti(ICLTerm *elt, int n, void* pc)
02301 {
02302 #ifdef NORMAL_GC
02303 CHECK_LEAKS();
02304 #endif
02305
02306
02307
02308
02309
02310
02311
02312
02313
02314
02315
02316
02317
02318
02319
02320
02321
02322
02323
02324
02325
02326
02327
02328
02329
02330
02331
02332
02333
02334 if (icl_IsValid(elt)) {
02335
02336 if ((elt->iclType == icl_int_type) ||
02337 (elt->iclType == icl_float_type) ||
02338 (elt->iclType == icl_var_type) ||
02339 (elt->iclType == icl_str_type) ||
02340 (elt->iclType == icl_dataq_type)) {
02341 if(elt->glibAlloc == 1) {
02342 g_free(elt->p);
02343 }
02344 else {
02345 free(elt->p);
02346 elt->p = NULL;
02347 }
02348 }
02349 else
02350
02351 if (elt->iclType == icl_struct_type) {
02352 ICLStructType *st = elt->p;
02353 icl_FreeTermMulti(st->functor, n + 1, pc);
02354 st->functor = NULL;
02355 icl_FreeTermMulti(st->args, n + 1, pc);
02356 free(elt->p);
02357 elt->p = NULL;
02358 }
02359 else
02360
02361 if (elt->iclType == icl_list_type) {
02362 ICLListType *list = elt->p;
02363 ICLListType *next;
02364 while (list) {
02365 icl_FreeTermMulti(list->elt, n + 1, pc);
02366 next = list->next;
02367 memset(list, 0, sizeof(ICLListType));
02368 free(list);
02369 list = next;
02370 }
02371 elt->p = NULL;
02372 }
02373
02374 if (elt->iclType == icl_group_type) {
02375 ICLGroupType *gp = elt->p;
02376 ICLListType *list = gp->list;
02377 ICLListType *next;
02378 free(gp->separator);
02379 gp->separator = NULL;
02380 while (list) {
02381 icl_FreeTermMulti(list->elt, n + 1, pc);
02382 next = list->next;
02383 list->next = NULL;
02384 memset(list, 0, sizeof(ICLListType));
02385 free(list);
02386 list = next;
02387 }
02388 free(gp);
02389 elt->p = NULL;
02390 }
02391
02392 memset(elt, 0, sizeof(ICLTerm));
02393 elt->magic_cookie = 0xdeadbeef;
02394 elt->iclType = icl_no_type;
02395 free(elt);
02396 #ifdef NORMAL_GC
02397 CHECK_LEAKS();
02398 #endif
02399 }
02400 }
02401
02402 #if 0
02403
02404
02405
02406
02407
02408
02409
02410
02411
02412
02413
02414
02415
02416
02417
02418
02419
02420
02421
02422 EXPORT_MSCPP
02423 ICLTerm * EXPORT_BORLAND
02424 icl_ReuseMem(ICLTerm *elt)
02425 {
02426 static ICLTerm *last = NULL;
02427
02428 icl_Free(last);
02429 last = elt;
02430 return elt;
02431 }
02432
02433 #endif
02434
02435
02436
02437
02438
02439
02443 EXPORT_MSCPP
02444 int EXPORT_BORLAND
02445 icl_IsList(ICLTerm const*elt)
02446 {
02447 return (icl_IsValid(elt) && (elt->iclType == icl_list_type));
02448 }
02449
02453 EXPORT_MSCPP
02454 int EXPORT_BORLAND
02455 icl_IsGroup(ICLTerm const*elt)
02456 {
02457 return (icl_IsValid(elt) && (elt->iclType == icl_group_type));
02458 }
02459
02463 EXPORT_MSCPP
02464 int EXPORT_BORLAND
02465 icl_IsStruct(ICLTerm const*elt)
02466 {
02467 return (icl_IsValid(elt) && (elt->iclType == icl_struct_type));
02468 }
02469
02470
02474 EXPORT_MSCPP
02475 int EXPORT_BORLAND
02476 icl_IsStr(ICLTerm const*elt)
02477 {
02478 return (icl_IsValid(elt) && (elt->iclType == icl_str_type));
02479 }
02480
02481
02485 EXPORT_MSCPP
02486 int EXPORT_BORLAND
02487 icl_IsVar(ICLTerm const*elt)
02488 {
02489 return (icl_IsValid(elt) && (elt->iclType == icl_var_type));
02490 }
02491
02492
02496 EXPORT_MSCPP
02497 int EXPORT_BORLAND
02498 icl_IsInt(ICLTerm const*elt)
02499 {
02500 return (icl_IsValid(elt) && (elt->iclType == icl_int_type));
02501 }
02502
02503
02507 EXPORT_MSCPP
02508 int EXPORT_BORLAND
02509 icl_IsFloat(ICLTerm const*elt)
02510 {
02511 return (icl_IsValid(elt) && (elt->iclType == icl_float_type));
02512 }
02513
02514 EXPORT_MSCPP
02515 int EXPORT_BORLAND
02516 icl_IsDataQ(ICLTerm const* elt)
02517 {
02518 return (icl_IsValid(elt) && (elt->iclType == icl_dataq_type));
02519 }
02520
02521
02525 EXPORT_MSCPP
02526 int EXPORT_BORLAND
02527 icl_IsValid(ICLTerm const*elt)
02528 {
02529 return (elt && (elt->magic_cookie == ICL_MAGIC_COOKIE));
02530 }
02531
02532
02533
02534
02535
02536
02537 int icl_IsGround(ICLTerm const *term)
02538 {
02539 ICLListType *plist = (ICLListType *)NULL;
02540
02541 if (! icl_IsValid(term))
02542 return FALSE;
02543
02544 if(icl_IsVar(term))
02545 return FALSE;
02546
02547 if(icl_IsStruct(term))
02548 plist = icl_Arguments(term);
02549 else if(icl_IsList(term))
02550 plist = icl_List(term);
02551
02552
02553
02554 while(icl_ListHasMoreElements(plist)) {
02555 ICLTerm *el = icl_ListElement(plist);
02556
02557 if(!icl_IsGround(el))
02558 return FALSE;
02559 plist = icl_ListNextElement(plist);
02560 }
02561 return TRUE;
02562 }
02563
02571 EXPORT_MSCPP
02572 void* EXPORT_BORLAND
02573 icl_DataQ(ICLTerm const* elt)
02574 {
02575 if(icl_IsDataQ(elt)) {
02576 return elt->p;
02577 }
02578 else {
02579 return NULL;
02580 }
02581 }
02582
02583 EXPORT_MSCPP
02584 size_t EXPORT_BORLAND
02585 icl_DataQLen(ICLTerm const* elt)
02586 {
02587 if(icl_IsDataQ(elt)) {
02588 return elt->len;
02589 }
02590 else {
02591 return 0;
02592 }
02593 }
02594
02598 EXPORT_MSCPP
02599 size_t EXPORT_BORLAND
02600 icl_Len(ICLTerm const *elt)
02601 {
02602 if(icl_IsValid(elt)) {
02603 return elt->len;
02604 }
02605 else {
02606 return 0;
02607 }
02608 }
02609
02614 EXPORT_MSCPP
02615 gint64 EXPORT_BORLAND
02616 icl_Int(ICLTerm const*elt)
02617 {
02618 gint64 *i;
02619
02620 if (icl_IsInt(elt)) {
02621 i = elt->p;
02622 return (*i);
02623 }
02624 else return(0);
02625 }
02626
02627
02632 EXPORT_MSCPP
02633 double EXPORT_BORLAND
02634 icl_Float(ICLTerm const*elt)
02635 {
02636 double *f;
02637
02638 if (icl_IsFloat(elt)) {
02639 f = elt->p;
02640 return (*f);
02641 }
02642 else return(0.0);
02643 }
02644
02645
02652 EXPORT_MSCPP
02653 char * EXPORT_BORLAND
02654 icl_Str(ICLTerm const*elt)
02655 {
02656 if (icl_IsStr(elt) || icl_IsVar(elt))
02657 return((char*)(elt->p));
02658 else
02659 if (icl_IsStruct(elt)) {
02660 ICLStructType *st = elt->p;
02661 return(icl_Str(st->functor));
02662 }
02663 else return(NULL);
02664 }
02665
02672 EXPORT_MSCPP
02673 char* EXPORT_BORLAND
02674 icl_Functor(ICLTerm const*elt)
02675 {
02676 if (icl_IsStruct(elt)) {
02677 ICLStructType *st = elt->p;
02678 return(icl_Str(st->functor));
02679 }
02680 else {
02681 return(NULL);
02682 }
02683 }
02684
02685
02690 EXPORT_MSCPP
02691 ICLListType * EXPORT_BORLAND
02692 icl_Arguments(ICLTerm const *elt)
02693 {
02694 if (icl_IsStruct(elt)) {
02695 ICLStructType *st = elt->p;
02696 return(icl_List(st->args));
02697 }
02698 else return(NULL);
02699 }
02700
02709 EXPORT_MSCPP
02710 int EXPORT_BORLAND
02711 icl_GetGroupChars(ICLTerm const*group, char *startC, char **sep)
02712 {
02713 if (icl_IsGroup(group)) {
02714 ICLGroupType *gt = group->p;
02715 *startC = gt->startChar;
02716 *sep = strdup(gt->separator);
02717 return(TRUE);
02718 }
02719 else return(FALSE);
02720 }
02721
02722
02728 EXPORT_MSCPP
02729 ICLListType * EXPORT_BORLAND
02730 icl_List(ICLTerm const*elt)
02731 {
02732 if (icl_IsList(elt)) {
02733 ICLListType *list = elt->p;
02734 return(list);
02735 }
02736 else
02737 if (icl_IsGroup(elt)) {
02738 ICLGroupType *gp = elt->p;
02739 ICLListType *list = gp->list;
02740 return(list);
02741 }
02742 else
02743 if (icl_IsStruct(elt)) {
02744 ICLStructType *st = elt->p;
02745 return(icl_List(st->args));
02746 }
02747 else return(NULL);
02748 }
02749
02750 EXPORT_MSCPP
02751 ICLListType * EXPORT_BORLAND icl_ListNext(ICLListType const* t)
02752 {
02753 return t->next;
02754 }
02755
02756 EXPORT_MSCPP
02757 ICLTerm * EXPORT_BORLAND icl_ListElt(ICLListType const* t)
02758 {
02759 return t->elt;
02760 }
02761
02762
02763 ICLListType* icl_copy_listtype(ICLListType* l)
02764 {
02765 ICLListType* newList = NULL;
02766 ICLListType* prev = NULL;
02767 while(l) {
02768 newList = (ICLListType*)malloc(sizeof(ICLListType));
02769 if(prev != NULL) {
02770 prev->next = newList;
02771 }
02772 newList->next = NULL;
02773 newList->elt = icl_CopyTerm(l->elt);
02774 l = l->next;
02775 prev = newList;
02776 }
02777 return newList;
02778 }
02779
02785 EXPORT_MSCPP
02786 ICLListType * EXPORT_BORLAND
02787 icl_ListCopy(ICLTerm const*elt)
02788 {
02789 if (icl_IsList(elt)) {
02790 ICLListType *list = elt->p;
02791 return(icl_copy_listtype(list));
02792 }
02793 else
02794 if (icl_IsGroup(elt)) {
02795 ICLGroupType *gp = elt->p;
02796 ICLListType *list = gp->list;
02797 return(icl_copy_listtype(list));
02798 }
02799 else
02800 if (icl_IsStruct(elt)) {
02801 ICLStructType *st = elt->p;
02802 return(icl_copy_listtype(icl_List(st->args)));
02803 }
02804 else {
02805 return(NULL);
02806 }
02807 }
02808
02809
02810
02811
02812
02813
02818 EXPORT_MSCPP
02819 int EXPORT_BORLAND
02820 icl_AddToList(ICLTerm *list, ICLTerm *elt, int atEnd)
02821 {
02822 if (icl_IsValid(elt) && (icl_IsList(list) || icl_IsGroup(list)) ) {
02823
02824
02825 if (icl_IsList(list) && !list->p) {
02826 list->p = icl_NewCons(elt, NULL);
02827 return TRUE;
02828 }
02829 else {
02830
02831 if (!atEnd) {
02832 list->p = icl_NewCons(elt, list->p);
02833 }
02834 else {
02835
02836 if (icl_IsGroup(list) && (!((ICLGroupType*)list->p)->list))
02837 ((ICLGroupType *)list->p)->list = icl_NewCons(elt, NULL);
02838
02839
02840 else {
02841 ICLListType *p;
02842 p = icl_List(list);
02843 while (p->next)
02844 p = p->next;
02845 p->next = icl_NewCons(elt, NULL);
02846 }
02847 }
02848 return (TRUE);
02849 }
02850 }
02851 else {
02852 return (FALSE);
02853 }
02854 }
02855
02860 EXPORT_MSCPP
02861 int EXPORT_BORLAND
02862 icl_ClearList(ICLTerm *list)
02863 {
02864 if ((icl_IsList(list) || icl_IsGroup(list)) ) {
02865 ICLListType *p;
02866 ICLListType *toBeDestroyed;
02867 ICLTerm* t;
02868
02869 p = icl_List(list);
02870 while (p) {
02871 toBeDestroyed = p;
02872 p = p->next;
02873 t = toBeDestroyed->elt;
02874 icl_Free(t);
02875 icl_stFree(toBeDestroyed);
02876 }
02877 return (TRUE);
02878 }
02879 return FALSE;
02880 }
02881
02886 EXPORT_MSCPP
02887 int EXPORT_BORLAND
02888 icl_SortList(ICLTerm *list, int (*user_function)(ICLTerm *Elt1, ICLTerm *Elt2))
02889 {
02890 (void)list;
02891 (void)user_function;
02892 return FALSE;
02893 }
02894
02898 EXPORT_MSCPP
02899 int EXPORT_BORLAND
02900 icl_ListHasMoreElements(ICLListType const*l)
02901 {
02902 if((l != NULL) &&
02903 (l->elt != NULL)) {
02904 return TRUE;
02905 }
02906 return FALSE;
02907 }
02908
02912 EXPORT_MSCPP
02913 ICLListType * EXPORT_BORLAND
02914 icl_ListNextElement(ICLListType const*l)
02915 {
02916 if(l)
02917 return l->next;
02918 else
02919 return NULL;
02920 }
02921
02925 EXPORT_MSCPP
02926 ICLTerm * EXPORT_BORLAND
02927 icl_ListElement(ICLListType const*list)
02928 {
02929 return list->elt;
02930 }
02931
02937 EXPORT_MSCPP
02938 int EXPORT_BORLAND
02939 icl_ListDelete(ICLTerm *list, ICLTerm *elem, ICLTerm **residue) {
02940 ICLListType *iterator;
02941 if(!icl_IsList(list))
02942 return FALSE;
02943 iterator = icl_List(list);
02944 *residue = icl_NewList(NULL);
02945 while(icl_ListHasMoreElements(iterator)) {
02946 ICLTerm *listel = icl_ListElement(iterator);
02947 if(!icl_Unify(listel, elem, NULL)) {
02948 icl_AddToList(*residue, icl_CopyTerm(listel), TRUE);
02949 }
02950 iterator = icl_ListNextElement(iterator);
02951 }
02952 return TRUE;
02953 }
02954
02958 EXPORT_MSCPP
02959 int EXPORT_BORLAND
02960 icl_AppendCopy(ICLTerm *list1, ICLTerm const*list2) {
02961
02962 if (list2==NULL)
02963 return FALSE;
02964
02965 if(icl_IsList(list1) && icl_IsList(list2)) {
02966 ICLListType *l2 = icl_List(list2);
02967 while(icl_ListHasMoreElements(l2)) {
02968 icl_AddToList(list1, icl_CopyTerm(icl_ListElement(l2)), TRUE);
02969 l2 = icl_ListNextElement(l2);
02970 }
02971 return TRUE;
02972 }
02973 return FALSE;
02974 }
02975
02979 EXPORT_MSCPP
02980 int EXPORT_BORLAND
02981 icl_Append(ICLTerm *list1, ICLTerm *list2) {
02982
02983
02984
02985
02986
02987
02988
02989
02990
02991
02992
02993 if (list2==NULL)
02994 return FALSE;
02995
02996 if(icl_IsList(list1) && icl_IsList(list2)) {
02997 ICLListType *l2 = icl_List(list2);
02998 while(icl_ListHasMoreElements(l2)) {
02999 icl_AddToList(list1, icl_ListElement(l2), TRUE);
03000 l2 = icl_ListNextElement(l2);
03001 }
03002 return TRUE;
03003 }
03004 return FALSE;
03005 }
03006
03012 EXPORT_MSCPP
03013 int EXPORT_BORLAND
03014 icl_Union(ICLTerm *list1, ICLTerm *list2, ICLTerm **dest)
03015 {
03016 ICLTerm* tmp;
03017 int res;
03018 if (list1 && list2 && icl_IsList(list1) && icl_IsList(list2)) {
03019 *dest = icl_CopyTerm(list1);
03020 tmp = *dest;
03021 res = icl_AppendCopy(*dest, list2);
03022 return TRUE;
03023 }
03024 return FALSE;
03025 }
03026
03033 EXPORT_MSCPP
03034 int EXPORT_BORLAND
03035 icl_Arity(ICLTerm const*elt)
03036 {
03037 return icl_NumTerms(elt);
03038 }
03039
03045 EXPORT_MSCPP
03046 int EXPORT_BORLAND
03047 icl_NumTerms(ICLTerm const*elt)
03048 {
03049 int len = 0;
03050
03051 if (icl_IsList(elt) || icl_IsGroup(elt) || icl_IsStruct(elt)) {
03052
03053 ICLListType *p;
03054
03055 p = icl_List(elt);
03056 while (p) {
03057 p = p->next;
03058 ++len;
03059 }
03060 }
03061
03062 return (len);
03063 }
03064
03071 EXPORT_MSCPP
03072 int EXPORT_BORLAND
03073 icl_ListLen(ICLTerm const*elt){
03074 return icl_NumTerms(elt);
03075 }
03076
03082 EXPORT_MSCPP
03083 ICLTerm * EXPORT_BORLAND icl_NthTerm(ICLTerm const*elt, int n)
03084 {
03085 ICLListType *p;
03086
03087 if (icl_IsList(elt) || icl_IsStruct(elt) || icl_IsGroup(elt))
03088 {
03089 if(!icl_IsValid(elt)) {
03090 return NULL;
03091 }
03092
03093 p = icl_List(elt);
03094 }
03095 else return (NULL);
03096
03097 while (p && (n > 1)) {
03098 p = p->next;
03099 --n;
03100 }
03101 if (p)
03102 return (p->elt);
03103 else
03104 return (NULL);
03105 }
03106
03112 EXPORT_MSCPP
03113 int EXPORT_BORLAND
03114 icl_NthTermAsInt(ICLTerm const*elt, int n, int *Value)
03115 {
03116 ICLTerm *v = icl_NthTerm(elt, n);
03117 if (v != NULL) {
03118 int tempInt = icl_Int(v);
03119 memcpy(Value, &tempInt, sizeof(int));
03120 return TRUE;
03121 }
03122 return FALSE;
03123 }
03124
03136 EXPORT_MSCPP
03137 int EXPORT_BORLAND
03138 icl_ParamValue(char *func, ICLTerm *match, ICLTerm *paramlist, ICLTerm **value)
03139 {
03140 ICLListType *p;
03141 ICLTerm *test = (ICLTerm *)NULL;
03142 int found = FALSE;
03143
03144
03145
03146 if (DEBUG_LEVEL > 7) {
03147 char *debugString = icl_NewStringFromTerm(paramlist);
03148
03149 printDebug(7, "icl_ParamValue : func %s\n", func);
03150 printDebug(7, "icl_ParamValue : paramlist %s\n", debugString);
03151 icl_stFree(debugString);
03152 }
03153
03154 if (icl_IsList(paramlist) && func && *func && (icl_NumTerms(paramlist)>0)) {
03155 p = icl_List(paramlist);
03156 }
03157 else {
03158 return FALSE;
03159 }
03160
03161 if (match) {
03162 test = icl_NewStruct(func, 1, icl_CopyTerm(match));
03163 }
03164 else {
03165 test = icl_NewStruct(func, 1, icl_NewVar("_"));
03166 }
03167
03168 while(p && !found) {
03169
03170
03171
03172 if (DEBUG_LEVEL > 7) {
03173 char *s1, *s2;
03174
03175 s1 = icl_NewStringStructFromTerm(test);
03176 s2 = icl_NewStringStructFromTerm(p->elt);
03177
03178 printDebug(7, "icl_ParamValue : %s VS %s\n", s1, s2);
03179 icl_stFree(s1);
03180 icl_stFree(s2);
03181 }
03182
03183
03184 found = icl_Unify(test, p->elt, value);
03185 p = p->next;
03186 }
03187
03188
03189 if (found && value && (DEBUG_LEVEL > 7)) {
03190 char *debugString = icl_NewStringFromTerm(*value);
03191
03192 printDebug(7, "Found %s\n", debugString);
03193 icl_stFree(debugString);
03194 }
03195
03196 icl_Free(test);
03197
03198 return (found);
03199 }
03200
03201
03206 EXPORT_MSCPP
03207 gint64 EXPORT_BORLAND
03208 icl_ParamValueAsInt(char *func, ICLTerm *paramlist, gint64 *Value)
03209 {
03210 ICLTerm *v = NULL;
03211 int result = FALSE;
03212
03213 if (Value && *Value &&
03214 icl_ParamValue(func, NULL, paramlist, &v)) {
03215 ICLTerm* temp_result = icl_NthTerm(v,1);
03216 if (icl_IsInt(temp_result)) {
03217 *Value = icl_Int(temp_result);
03218 result = TRUE;
03219 }
03220 }
03221 icl_Free(v);
03222 return result;
03223 }
03224
03225
03231 EXPORT_MSCPP
03232 int EXPORT_BORLAND
03233 icl_Member(ICLTerm const*elt, ICLTerm const*list, ICLTerm **res)
03234 {
03235 ICLListType *p;
03236 int found = FALSE;
03237
03238 if (icl_IsList(list) && elt) {
03239 p = icl_List(list);
03240 }
03241 else {
03242 return FALSE;
03243 }
03244
03245 while(p && !found) {
03246 found = icl_Unify(elt, p->elt, res);
03247 p = p->next;
03248 }
03249
03250 return found;
03251 }
03252
03253
03254
03255
03256
03257
03258
03259
03260
03261
03262
03263
03264
03265
03266
03267
03268
03269 static
03270 void icl_bind_var(ICLTerm *var,
03271 ICLTerm *value,
03272 struct dyn_array *vars)
03273 {
03274 icl_append_dyn_array(vars, strdup(icl_Str(var)));
03275 icl_append_dyn_array(vars, icl_CopyTerm(value));
03276 }
03277
03278
03279
03280
03281
03282
03283
03284
03285
03286 static
03287 void icl_deref(ICLTerm **var,
03288 struct dyn_array var_bindings)
03289 {
03290 int done = 0;
03291 int pos;
03292
03293 do {
03294 if (!icl_IsVar(*var)) {
03295 return;
03296 }
03297
03298 pos = icl_member_strlist(icl_Str(*var), var_bindings, 2, 0);
03299 if (pos >= 0) {
03300 *var = (ICLTerm *)var_bindings.item[pos+1];
03301 }
03302 else {
03303 done = 1;
03304 }
03305 } while (!done);
03306
03307 return;
03308 }
03309
03310
03322 EXPORT_MSCPP
03323 int EXPORT_BORLAND icl_match_terms(ICLTerm *t1, ICLTerm *t2, struct dyn_array *vars)
03324 {
03325 int res;
03326 ICLListType *l1, *l2;
03327
03328
03329 if (!icl_IsValid(t1) || !icl_IsValid(t2)) {
03330 return FALSE;
03331 }
03332
03333 if (vars) {
03334 icl_deref(&t1, *vars);
03335 icl_deref(&t2, *vars);
03336 }
03337
03338 if (icl_IsVar(t1)) {
03339
03340 if (vars) {
03341
03342 icl_bind_var(t1, t2, vars);
03343 }
03344 return TRUE;
03345 }
03346 else if (icl_IsVar(t2)) {
03347
03348 if (vars) {
03349
03350 icl_bind_var(t2, t1, vars);
03351 }
03352 return TRUE;
03353 }
03354 else if (t1->iclType == t2->iclType) {
03355
03356 if (t1->iclType == icl_float_type) {
03357 return (icl_Float(t1) == icl_Float(t2));
03358 }
03359 else if (t1->iclType == icl_int_type) {
03360 return (icl_Int(t1) == icl_Int(t2));
03361 }
03362 else if (t1->iclType == icl_str_type) {
03363 return (strcmp(icl_Str(t1), icl_Str(t2)) == 0);
03364 }
03365 else {
03366 if (t1->iclType == icl_struct_type) {
03367 if (strcmp(icl_Str(t1), icl_Str(t2)) != 0) {
03368 return FALSE;
03369 }
03370 }
03371
03372 if ((t1->iclType == icl_list_type) ||
03373 (t1->iclType == icl_group_type) ||
03374 (t1->iclType == icl_struct_type)) {
03375
03376 l1 = icl_List(t1);
03377 l2 = icl_List(t2);
03378 res = TRUE;
03379
03380 while (l1 && l2 && res) {
03381 res = icl_match_terms(l1->elt, l2->elt, vars);
03382 l1 = l1->next;
03383 l2 = l2->next;
03384 }
03385
03386 return(!l1 && !l2 && res);
03387 }
03388 else {
03389 return FALSE;
03390 }
03391 }
03392 }
03393 else {
03394
03395 return FALSE;
03396 }
03397 }
03398
03399 EXPORT_MSCPP
03400 int EXPORT_BORLAND icl_match_terms_DEBUG(ICLTerm *t1, ICLTerm *t2, struct dyn_array *vars)
03401 {
03402 int res;
03403 ICLListType *l1, *l2;
03404
03405 printf("icl_match_terms_DEBUG\n");
03406
03407
03408 if (!icl_IsValid(t1) || !icl_IsValid(t2)) {
03409 printf("icl_match_terms_DEBUG One or the other is invalid\n");
03410 return FALSE;
03411 }
03412
03413 if (vars) {
03414 icl_deref(&t1, *vars);
03415 icl_deref(&t2, *vars);
03416 }
03417
03418 if (icl_IsVar(t1)) {
03419
03420 if (vars) {
03421
03422 icl_bind_var(t1, t2, vars);
03423 }
03424 return TRUE;
03425 }
03426 else if (icl_IsVar(t2)) {
03427
03428 if (vars) {
03429
03430 icl_bind_var(t2, t1, vars);
03431 }
03432 return TRUE;
03433 }
03434 else if (t1->iclType == t2->iclType) {
03435
03436 if (t1->iclType == icl_float_type) {
03437 printf("icl_match_terms_DEBUG floats == %i\n", icl_Float(t1) == icl_Float(t2));
03438 return (icl_Float(t1) == icl_Float(t2));
03439 }
03440 else if (t1->iclType == icl_int_type) {
03441 printf("icl_match_terms_DEBUG ints == %i\n", icl_Int(t1) == icl_Int(t2));
03442 return (icl_Int(t1) == icl_Int(t2));
03443 }
03444 else if (t1->iclType == icl_str_type) {
03445 printf("icl_match_terms_DEBUG string types strcmp(%s,%s) = %i\n",
03446 icl_Str(t1), icl_Str(t2),
03447 strcmp(icl_Str(t1), icl_Str(t2)));
03448 return (strcmp(icl_Str(t1), icl_Str(t2)) == 0);
03449 }
03450 else {
03451 if (t1->iclType == icl_struct_type) {
03452 if (strcmp(icl_Str(t1), icl_Str(t2)) != 0) {
03453 printf("icl_match_terms_DEBUG mismatched struct names\n");
03454 return FALSE;
03455 }
03456 }
03457
03458 if ((t1->iclType == icl_list_type) ||
03459 (t1->iclType == icl_group_type) ||
03460 (t1->iclType == icl_struct_type)) {
03461
03462 l1 = icl_List(t1);
03463 l2 = icl_List(t2);
03464 res = TRUE;
03465
03466 while (l1 && l2 && res) {
03467 res = icl_match_terms_DEBUG(l1->elt, l2->elt, vars);
03468 l1 = l1->next;
03469 l2 = l2->next;
03470 }
03471
03472 return(!l1 && !l2 && res);
03473 }
03474 else {
03475 printf("icl_match_terms_DEBUG bad type\n");
03476 return FALSE;
03477 }
03478 }
03479 }
03480 else {
03481
03482 printf("icl_match_terms_DEBUG different types: %i, %i\n", t1->iclType, t2->iclType);
03483 return FALSE;
03484 }
03485 }
03486
03487
03503 EXPORT_MSCPP
03504 int EXPORT_BORLAND icl_Unify(ICLTerm const*t1, ICLTerm const*t2, ICLTerm **answer)
03505 {
03506 struct dyn_array da;
03507 int result;
03508 int i;
03509
03510 ICLTerm* renamed_t1 = icl_CopyTerm(t1);
03511 ICLTerm* renamed_t2 = icl_CopyTerm(t2);
03512 ICLTerm* toFree;
03513
03514 da.count = 0;
03515
03516
03517
03518
03519 rename_vars_index=0;
03520 icl_rename_vars_term(&renamed_t1);
03521 icl_rename_vars_term(&renamed_t2);
03522
03523 icl_init_dyn_array(&da);
03524
03525 result = icl_match_terms(renamed_t1, renamed_t2, &da);
03526
03527 if (result && answer) {
03528 CHECK_LEAKS();
03529 *answer = icl_copy_term(renamed_t1, &da);
03530 CHECK_LEAKS();
03531 }
03532
03533
03534
03535 for (i = 0; i < (da).count; i = i + 2) {
03536 free((da).item[i]);
03537 toFree = (ICLTerm*)(da.item[i + 1]);
03538 icl_Free(toFree);
03539 }
03540 free((da).item);
03541
03542 icl_Free(renamed_t1);
03543 icl_Free(renamed_t2);
03544
03545 CHECK_LEAKS();
03546 return result;
03547 }
03548
03549 EXPORT_MSCPP
03550 int EXPORT_BORLAND icl_Unify_DEBUG(ICLTerm *t1, ICLTerm *t2, ICLTerm **answer)
03551 {
03552 struct dyn_array da;
03553 int result;
03554 int i;
03555
03556 ICLTerm* renamed_t1 = icl_CopyTerm(t1);
03557 ICLTerm* renamed_t2 = icl_CopyTerm(t2);
03558 ICLTerm* toFree;
03559
03560
03561
03562
03563
03564 rename_vars_index=0;
03565 icl_rename_vars_term(&renamed_t1);
03566 icl_rename_vars_term(&renamed_t2);
03567
03568 icl_init_dyn_array(&da);
03569
03570 result = icl_match_terms_DEBUG(renamed_t1, renamed_t2, &da);
03571 printf("result = %i\n", result);
03572
03573 if (result && answer) {
03574 *answer = icl_copy_term(renamed_t1, &da);
03575 }
03576
03577
03578
03579 for (i = 0; i < (da).count; i = i + 2) {
03580 free((da).item[i]);
03581 toFree = (ICLTerm*)(da.item[i + 1]);
03582 icl_Free(toFree);
03583 }
03584 free((da).item);
03585
03586 icl_Free(renamed_t1);
03587 icl_Free(renamed_t2);
03588
03589 return result;
03590 }
03591
03592
03593
03594
03595
03596
03601 EXPORT_MSCPP
03602 int EXPORT_BORLAND
03603 icl_WriteTerm(ICLTerm *t)
03604 {
03605 if (icl_IsValid(t)) {
03606 char *s = icl_NewStringFromTerm(t);
03607 int res = (s != NULL);
03608
03609 printf(s);
03610
03611 icl_stFree(s);
03612 return res;
03613 }
03614 else return FALSE;
03615 }
03616
03617
03618
03619
03620
03625 EXPORT_MSCPP
03626 ICLTerm * EXPORT_BORLAND
03627 icl_True()
03628 {
03629 static ICLTerm *icl_true = NULL;
03630
03631
03632 if (!icl_IsValid(icl_true)) {
03633 icl_true = icl_NewStr("true");
03634 return icl_true;
03635 }
03636 else return icl_true;
03637 }
03638
03639 EXPORT_MSCPP
03640 ICLTerm * EXPORT_BORLAND
03641 icl_False()
03642 {
03643 static ICLTerm *icl_false = NULL;
03644
03645
03646 if (!icl_IsValid(icl_false)) {
03647 icl_false = icl_NewStr("false");
03648 return icl_false;
03649 }
03650 else return icl_false;
03651 }
03652
03653 EXPORT_MSCPP
03654 ICLTerm * EXPORT_BORLAND
03655 icl_Empty()
03656 {
03657 static ICLTerm *icl_empty = NULL;
03658
03659
03660 if (!icl_IsValid(icl_empty)) {
03661 icl_empty = icl_NewList(NULL);
03662 return icl_empty;
03663 }
03664 else {
03665 return icl_empty;
03666 }
03667 }
03668
03669 EXPORT_MSCPP
03670 ICLTerm * EXPORT_BORLAND
03671 icl_Var()
03672 {
03673 static ICLTerm *icl_var = NULL;
03674
03675
03676 if (icl_var && !icl_IsVar(icl_var)){
03677 icl_Free(icl_var);
03678
03679 }
03680
03681 if (!icl_IsValid(icl_var)) {
03682 icl_var = icl_NewVar("_");
03683 return icl_var;
03684 }
03685 else return icl_var;
03686 }
03687
03688
03689
03690
03691
03692
03696 int icl_list_has_more_elements(ICLListType *l)
03697 {
03698 if(l && (l->elt != NULL))
03699 return TRUE;
03700 return FALSE;
03701 }
03702
03706 ICLListType *icl_list_next_element(ICLListType *l)
03707 {
03708 if(l)
03709 return l->next;
03710 else
03711 return NULL;
03712 }
03713
03717 ICLTerm *icl_list_element(ICLListType *list)
03718 {
03719 return list->elt;
03720 }
03721
03726 int icl_list_delete(ICLTerm *list, ICLTerm *elem, ICLTerm **residue)
03727 {
03728 ICLListType *iterator;
03729 if(!icl_IsList(list))
03730 return FALSE;
03731 iterator = icl_List(list);
03732 *residue = icl_NewList(NULL);
03733 while(icl_list_has_more_elements(iterator)) {
03734 ICLTerm *listel = icl_list_element(iterator);
03735 if(!icl_Unify(listel, elem, NULL)) {
03736 icl_AddToList(*residue, listel, TRUE);
03737 }
03738 iterator = icl_list_next_element(iterator);
03739 }
03740 return TRUE;
03741 }
03742
03746 int icl_append_to_list(ICLTerm *list1, ICLTerm *list2, ICLTerm **list3)
03747 {
03748 ICLListType *l2;
03749
03750 if (!icl_IsList(list2) || !icl_IsList(list1)) {
03751 return FALSE;
03752 }
03753
03754 *list3 = icl_CopyTerm(list1);
03755 l2 = icl_List(list2);
03756
03757 while(icl_ListHasMoreElements(l2)) {
03758 icl_AddToList(*list3, icl_CopyTerm(icl_ListElement(l2)), TRUE);
03759 l2 = icl_ListNextElement(l2);
03760 }
03761 return TRUE;
03762 }
03763
03770 EXPORT_MSCPP
03771 ICLTerm* icl_GenerateSimpleUnifyingTerm(ICLTerm const*term)
03772 {
03773 ICLTerm* newTerm = NULL;
03774 int numTerms;
03775
03776 if(!(icl_IsList(term) || icl_IsGroup(term) || icl_IsStruct(term))) {
03777 return icl_NewVar("_");
03778 }
03779
03780 numTerms = icl_NumTerms(term);
03781
03782 if(icl_IsStruct(term)) {
03783 char* functor = icl_Functor(term);
03784 ICLTerm* args = icl_NewList(NULL);
03785 {
03786 int i;
03787 for(i = 0; i < numTerms; ++i) {
03788 icl_AddToList(args, icl_NewVar("_"), TRUE);
03789 }
03790 }
03791 newTerm = icl_NewStructFromList(functor, args);
03792 }
03793 else {
03794 int i;
03795 newTerm = icl_CopyTerm(term);
03796 for(i = 0; i < numTerms; ++i) {
03797 icl_ReplaceElement(newTerm, i, icl_NewVar("_"), TRUE);
03798 }
03799 }
03800
03801 return newTerm;
03802 }
03803
03810 EXPORT_MSCPP
03811 int icl_ReplaceElement(ICLTerm* term, int index, ICLTerm* replacement, int freeReplaced)
03812 {
03813 if(!(icl_IsList(term) || icl_IsGroup(term) || icl_IsStruct(term))) {
03814 return FALSE;
03815 }
03816 else {
03817 ICLListType *p = icl_List(term);
03818 int i;
03819 for(i = 0; p && i < index; ++i) {
03820 p = p->next;
03821 }
03822 if(i != index) {
03823 return FALSE;
03824 }
03825 if(freeReplaced && p->elt) {
03826 icl_FreeTerm(p->elt);
03827 }
03828 p->elt = replacement;
03829
03830 return TRUE;
03831 }
03832 }
03833
03839 EXPORT_MSCPP
03840 int icl_ReplaceUnifying(ICLTerm* term, ICLTerm const* selector, ICLTerm const* replacement, int freeReplaced)
03841 {
03842 if(!(icl_IsList(term) || icl_IsGroup(term) || icl_IsStruct(term))) {
03843 return FALSE;
03844 }
03845 else {
03846 ICLListType *p;
03847 int numReplaced = 0;
03848 for(p = icl_List(term); p; p = p->next) {
03849 if(icl_Unify(p->elt, selector, NULL)) {
03850 if(freeReplaced) {
03851 icl_FreeTerm(p->elt);
03852 }
03853 p->elt = icl_CopyTerm(replacement);
03854 ++numReplaced;
03855 }
03856 }
03857 return numReplaced;
03858 }
03859 }
03860