1 /////////////////////////////////////////////////////////////////////////////
4 // Author: Julian Smart
8 // Copyright: (c) Julian Smart and Markus Holzem
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
13 #pragma implementation "wxexpr.h"
16 // For compilers that support precompilation, includes "wx/wx.h".
17 #include "wx/wxprec.h"
29 #include "wx/wxexpr.h"
31 extern "C" void add_expr(char *);
32 extern "C" void LexFromFile(FILE *fd
);
33 extern "C" void LexFromString(char *buf
);
37 /* Rename all YACC/LEX stuff or we'll conflict with other
41 #define yyback PROIO_yyback
42 #define yylook PROIO_yylook
43 #define yywrap PROIO_yywrap
44 #define yyoutput PROIO_yyoutput
45 #define yylex PROIO_yylex
46 #define yyerror PROIO_yyerror
47 #define yyleng PROIO_yyleng
48 #define yytext PROIO_yytext
49 #define yymorfg PROIO_yymorfg
50 #define yylineno PROIO_yylineno
51 #define yytchar PROIO_yytchar
52 #define yyin PROIO_yyin
53 #define yyout PROIO_yyout
54 #define yysvf PROIO_yysvf
55 #define yyestate PROIO_yyestate
56 #define yysvec PROIO_yysvec
57 #define yybgin PROIO_yybgin
58 #define yyprevious PROIO_yyprevious
59 #define yylhs PROIO_yylhs
60 #define yylen PROIO_yylen
61 #define yydefred PROIO_yydefred
62 #define yydgoto PROIO_yydgoto
63 #define yysindex PROIO_yysindex
64 #define yyrindex PROIO_yyrindex
65 #define yygindex PROIO_yygindex
66 #define yytable PROIO_yytable
67 #define yycheck PROIO_yycheck
68 #define yyname PROIO_yyname
69 #define yyrule PROIO_yyrule
70 #define yydebug PROIO_yydebug
71 #define yynerrs PROIO_yynerrs
72 #define yyerrflag PROIO_yyerrflag
73 #define yychar PROIO_yychar
74 #define yyvsp PROIO_yyvsp
75 #define yyssp PROIO_yyssp
76 #define yyval PROIO_yyval
77 #define yylval PROIO_yylval
78 #define yyss PROIO_yyss
79 #define yyvs PROIO_yyvs
80 #define yyparse PROIO_yyparse
82 /* +++steve162e: more defines necessary */
83 #define yy_init_buffer PROIO_yy_init_buffer
84 #define yy_create_buffer PROIO_yy_create_buffer
85 #define yy_load_buffer_state PROIO_yy_load_buffer_state
86 #define yyrestart PROIO_yyrestart
87 #define yy_switch_to_buffer PROIO_yy_switch_to_buffer
88 #define yy_delete_buffer PROIO_yy_delete_buffer
91 /* WG 1/96: still more for flex 2.5 */
92 #define yy_scan_buffer PROIO_scan_buffer
93 #define yy_scan_string PROIO_scan_string
94 #define yy_scan_bytes PROIO_scan_bytes
95 #define yy_flex_debug PROIO_flex_debug
96 #define yy_flush_buffer PROIO_flush_buffer
97 #if !defined(__VISAGECPP__)
98 /* multiply defined??? */
99 #define yyleng PROIO_yyleng
100 #define yytext PROIO_yytext
103 extern "C" WXDLLEXPORT_DATA(FILE*) yyin
;
104 extern "C" WXDLLEXPORT
int yyparse(void);
107 wxExprDatabase
*thewxExprDatabase
= NULL
;
108 wxExprErrorHandler currentwxExprErrorHandler
;
110 wxExpr::wxExpr(const wxString
& functor
)
117 wxExpr
*pfunctor
= new wxExpr(wxExprWord
, functor
);
122 wxExpr::wxExpr(wxExprType the_type
, const wxString
& word_or_string
)
129 value
.word
= copystring((const wxChar
*)word_or_string
);
132 value
.string
= copystring((const wxChar
*)word_or_string
);
147 wxExpr::wxExpr(wxExprType the_type
, wxChar
*word_or_string
, bool allocate
)
154 value
.word
= allocate
? copystring(word_or_string
) : word_or_string
;
157 value
.string
= allocate
? copystring(word_or_string
) : word_or_string
;
172 wxExpr::wxExpr(long the_integer
)
174 type
= wxExprInteger
;
175 value
.integer
= the_integer
;
180 wxExpr::wxExpr(double the_real
)
183 value
.real
= the_real
;
188 wxExpr::wxExpr(wxList
*the_list
)
195 wxExpr
*listExpr
= new wxExpr(wxExprList
);
197 wxNode
*node
= the_list
->First();
200 wxExpr
*expr
= (wxExpr
*)node
->Data();
201 listExpr
->Append(expr
);
209 wxExpr::~wxExpr(void)
220 delete[] value
.string
;
230 wxExpr
*expr
= value
.first
;
233 wxExpr
*expr1
= expr
->next
;
240 case wxExprNull
: break;
244 void wxExpr::Append(wxExpr
*expr
)
254 void wxExpr::Insert(wxExpr
*expr
)
256 expr
->next
= value
.first
;
263 wxExpr
*wxExpr::Copy(void) const
265 // This seems to get round an optimizer bug when
266 // using Watcom C++ 10a in WIN32 compilation mode.
267 // If these lines not present, the type seems to be
268 // interpreted wrongly as an integer.
269 // I don't want to turn optimization off since it's needed
270 // for reading in files quickly.
271 #if defined(__WATCOMC__)
279 return new wxExpr(value
.integer
);
281 return new wxExpr(value
.real
);
283 return new wxExpr(wxExprString
, wxString(value
.string
));
285 return new wxExpr(wxExprWord
, wxString(value
.word
));
288 wxExpr
*expr
= value
.first
;
289 wxExpr
*new_list
= new wxExpr(wxExprList
);
292 wxExpr
*expr2
= expr
->Copy();
293 new_list
->Append(expr2
);
305 // Get the wxExpr (containing (= wxExpr Value) form) for the given word
306 // or string, assuming that we have Attribute=Value, ...
307 wxExpr
*wxExpr::GetAttributeValueNode(const wxString
& word
) const // Use only for a clause or list
309 if (type
!= wxExprList
)
312 wxExpr
*expr
= value
.first
;
315 if (expr
->type
== wxExprList
)
317 wxExpr
*firstNode
= expr
->value
.first
;
318 if ((firstNode
->type
== wxExprWord
) && (firstNode
->value
.word
[0] == '='))
320 wxExpr
*secondNode
= firstNode
->next
;
321 if ((secondNode
->type
== wxExprWord
) &&
322 (wxStrcmp((const wxChar
*)word
, secondNode
->value
.word
) == 0))
333 // Get the value (in wxExpr form) for the given word or string, assuming
334 // that we have Attribute=Value, ...
335 wxExpr
*wxExpr::AttributeValue(const wxString
& word
) const // Use only for a clause or list
337 if (type
!= wxExprList
)
340 wxExpr
*attExpr
= GetAttributeValueNode(word
);
341 if (attExpr
&& attExpr
->value
.first
&& attExpr
->value
.first
->next
)
342 return attExpr
->value
.first
->next
->next
;
346 wxString
wxExpr::Functor(void) const // Use only for a clause
348 if ((type
!= wxExprList
) || !value
.first
)
349 return wxString(wxT(""));
351 if (value
.first
->type
== wxExprWord
)
352 return wxString(value
.first
->value
.word
);
354 return wxString(wxT(""));
357 bool wxExpr::IsFunctor(const wxString
& f
) const // Use only for a clause
359 if ((type
!= wxExprList
) || !value
.first
)
362 return (value
.first
->type
== wxExprWord
&&
363 (wxStrcmp((const wxChar
*)f
, value
.first
->value
.word
) == 0));
366 // Return nth argument of a clause (starting from 1)
367 wxExpr
*wxExpr::Arg(wxExprType theType
, int arg
) const
369 wxExpr
*expr
= value
.first
;
371 for (i
= 1; i
< arg
; i
++)
375 if (expr
&& (expr
->type
== theType
))
381 // Return nth argument of a list expression (starting from zero)
382 wxExpr
*wxExpr::Nth(int arg
) const
384 if (type
!= wxExprList
)
387 wxExpr
*expr
= value
.first
;
389 for (i
= 0; i
< arg
; i
++)
400 // Returns the number of elements in a list expression
401 int wxExpr::Number(void) const
403 if (type
!= wxExprList
)
407 wxExpr
*expr
= value
.first
;
416 void wxExpr::DeleteAttributeValue(const wxString
& attribute
)
418 if (type
!= wxExprList
)
421 wxExpr
*expr
= value
.first
;
422 wxExpr
*lastExpr
= this;
425 if (expr
->type
== wxExprList
)
427 wxExpr
*firstNode
= expr
->value
.first
;
428 if ((firstNode
->type
== wxExprWord
) && (firstNode
->value
.word
[0] == '='))
430 wxExpr
*secondNode
= firstNode
->next
;
431 if ((secondNode
->type
== wxExprWord
) &&
432 (wxStrcmp((const wxChar
*)attribute
, secondNode
->value
.word
) == 0))
434 wxExpr
*nextExpr
= expr
->next
;
437 lastExpr
->next
= nextExpr
;
452 void wxExpr::AddAttributeValue(const wxString
& attribute
, wxExpr
*val
)
454 if (type
!= wxExprList
)
456 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
459 // Warning - existing code may assume that any existing value
460 // is deleted first. For efficiency, we leave this to the application.
461 // DeleteAttributeValue(attribute);
463 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
464 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
466 wxExpr
*listExpr
= new wxExpr(wxExprList
);
468 listExpr
->Append(pequals
);
469 listExpr
->Append(patt
);
470 listExpr
->Append(val
);
475 void wxExpr::AddAttributeValue(const wxString
& attribute
, long val
)
477 if (type
!= wxExprList
)
479 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
482 // Warning - existing code may assume that any existing value
483 // is deleted first. For efficiency, we leave this to the application.
484 // DeleteAttributeValue(attribute);
486 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
487 wxExpr
*pval
= new wxExpr(val
);
488 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
490 wxExpr
*listExpr
= new wxExpr(wxExprList
);
492 listExpr
->Append(pequals
);
493 listExpr
->Append(patt
);
494 listExpr
->Append(pval
);
499 void wxExpr::AddAttributeValue(const wxString
& attribute
, double val
)
501 if (type
!= wxExprList
)
503 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
507 // DeleteAttributeValue(attribute);
508 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
509 wxExpr
*pval
= new wxExpr(val
);
510 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
512 wxExpr
*listExpr
= new wxExpr(wxExprList
);
514 listExpr
->Append(pequals
);
515 listExpr
->Append(patt
);
516 listExpr
->Append(pval
);
521 void wxExpr::AddAttributeValueString(const wxString
& attribute
, const wxString
& val
)
523 if (type
!= wxExprList
)
525 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
529 // DeleteAttributeValue(attribute);
531 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
532 wxExpr
*pval
= new wxExpr(wxExprString
, val
);
533 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
535 wxExpr
*listExpr
= new wxExpr(wxExprList
);
537 listExpr
->Append(pequals
);
538 listExpr
->Append(patt
);
539 listExpr
->Append(pval
);
544 void wxExpr::AddAttributeValueWord(const wxString
& attribute
, const wxString
& val
)
546 if (type
!= wxExprList
)
548 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
552 // DeleteAttributeValue(attribute);
554 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
555 wxExpr
*pval
= new wxExpr(wxExprWord
, val
);
556 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
558 wxExpr
*listExpr
= new wxExpr(wxExprList
);
560 listExpr
->Append(pequals
);
561 listExpr
->Append(patt
);
562 listExpr
->Append(pval
);
567 void wxExpr::AddAttributeValue(const wxString
& attribute
, wxList
*val
)
569 if (type
!= wxExprList
)
571 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
577 // DeleteAttributeValue(attribute);
579 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
580 wxExpr
*pval
= new wxExpr(val
);
581 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
583 wxExpr
*listExpr
= new wxExpr(wxExprList
);
585 listExpr
->Append(pequals
);
586 listExpr
->Append(patt
);
587 listExpr
->Append(pval
);
592 void wxExpr::AddAttributeValueStringList(const wxString
& attribute
, wxList
*string_list
)
594 if (type
!= wxExprList
)
596 // cout << "Error! tried to add an attribute-value pair to a nonlist wxExpr expression\n";
602 // DeleteAttributeValue(attribute);
604 // First make a list of wxExpr strings
605 wxExpr
*listExpr
= new wxExpr(wxExprList
);
606 wxNode
*node
= string_list
->First();
609 char *string
= (char *)node
->Data();
610 wxExpr
*expr
= new wxExpr(wxExprString
, wxString(string
));
611 listExpr
->Append(expr
);
615 // Now make an (=, Att, Value) triple
616 wxExpr
*patt
= new wxExpr(wxExprWord
, attribute
);
617 wxExpr
*pequals
= new wxExpr(wxExprWord
, wxT("="));
619 wxExpr
*listExpr2
= new wxExpr(wxExprList
);
621 listExpr2
->Append(pequals
);
622 listExpr2
->Append(patt
);
623 listExpr2
->Append(listExpr
);
628 bool wxExpr::GetAttributeValue(const wxString
& att
, int& var
) const
630 wxExpr
*expr
= AttributeValue(att
);
632 if (expr
&& (expr
->Type() == wxExprInteger
|| expr
->Type() == wxExprReal
))
634 var
= (int)(expr
->IntegerValue());
641 bool wxExpr::GetAttributeValue(const wxString
& att
, long& var
) const
643 wxExpr
*expr
= AttributeValue(att
);
645 if (expr
&& (expr
->Type() == wxExprInteger
|| expr
->Type() == wxExprReal
))
647 var
= expr
->IntegerValue();
654 bool wxExpr::GetAttributeValue(const wxString
& att
, float& var
) const
656 wxExpr
*expr
= AttributeValue(att
);
657 if (expr
&& (expr
->Type() == wxExprInteger
|| expr
->Type() == wxExprReal
))
659 var
= (float) expr
->RealValue();
666 bool wxExpr::GetAttributeValue(const wxString
& att
, double& var
) const
668 wxExpr
*expr
= AttributeValue(att
);
669 if (expr
&& (expr
->Type() == wxExprInteger
|| expr
->Type() == wxExprReal
))
671 var
= expr
->RealValue();
678 bool wxExpr::GetAttributeValue(const wxString
& att
, wxString
& var
) const // Word OR string -> string
680 wxExpr
*expr
= AttributeValue(att
);
681 if (expr
&& expr
->Type() == wxExprWord
)
683 var
= expr
->WordValue();
686 else if (expr
&& expr
->Type() == wxExprString
)
688 var
= expr
->StringValue();
695 bool wxExpr::GetAttributeValue(const wxString
& att
, wxExpr
**var
) const
697 wxExpr
*expr
= AttributeValue(att
);
707 bool wxExpr::GetAttributeValueStringList(const wxString
& att
, wxList
*var
) const
709 wxExpr
*expr
= AttributeValue(att
);
710 if (expr
&& expr
->Type() == wxExprList
)
712 wxExpr
*string_expr
= expr
->value
.first
;
715 if (string_expr
->Type() == wxExprString
)
716 var
->Append((wxObject
*)copystring(string_expr
->StringValue()));
718 string_expr
= string_expr
->next
;
727 void wxExpr::AssignAttributeValue(wxChar
*att
, wxChar
**var
) const
730 if (GetAttributeValue(att
, str
))
734 *var
= copystring((const wxChar
*) str
);
738 void wxExpr::WriteClause(FILE* stream
) // Write this expression as a top-level clause
740 if (type
!= wxExprList
)
743 wxExpr
*node
= value
.first
;
746 node
->WriteExpr(stream
);
747 fprintf( stream
, "(" );
753 fprintf( stream
, " " );
754 node
->WriteExpr(stream
);
757 fprintf( stream
, ",\n" );
760 fprintf( stream
, ").\n\n" );
764 void wxExpr::WriteExpr(FILE* stream
) // Write as any other subexpression
766 // This seems to get round an optimizer bug when
767 // using Watcom C++ 10a in WIN32 compilation mode.
768 // If these lines not present, the type seems to be
769 // interpreted wrongly as an integer.
770 // I don't want to turn optimization off since it's needed
771 // for reading in files quickly.
772 #if defined(__WATCOMC__)
781 fprintf( stream
, "%ld", value
.integer
);
786 double f
= value
.real
;
787 fprintf( stream
, "%.6g", f
);
792 fprintf( stream
, "\"" );
794 const wxWX2MBbuf val
= wxConvLibc
.cWX2MB(value
.string
);
795 size_t len
= strlen(val
);
796 for (i
= 0; i
< len
; i
++)
799 if (ch
== '"' || ch
== '\\')
800 fprintf( stream
, "\\" );
804 fprintf( stream
, tmp
);
806 fprintf( stream
, "\"" );
811 bool quote_it
= FALSE
;
812 const wxWX2MBbuf val
= wxConvLibc
.cWX2MB(value
.word
);
813 size_t len
= strlen(val
);
814 if ((len
== 0) || (len
> 0 && (val
[(size_t) 0] > 64 && val
[(size_t) 0] < 91)))
819 for (i
= 0; i
< len
; i
++)
820 if ((!isalpha(val
[i
])) && (!isdigit(val
[i
])) &&
822 { quote_it
= TRUE
; i
= len
; }
826 fprintf( stream
,"'" );
828 fprintf( stream
, val
);
831 fprintf( stream
, "'" );
838 fprintf( stream
, "[]" );
841 wxExpr
*expr
= value
.first
;
843 if ((expr
->Type() == wxExprWord
) && (wxStrcmp(expr
->WordValue(), wxT("=")) == 0))
845 wxExpr
*arg1
= expr
->next
;
846 wxExpr
*arg2
= arg1
->next
;
847 arg1
->WriteExpr(stream
);
848 fprintf( stream
, " = " );
849 arg2
->WriteExpr(stream
);
853 fprintf( stream
, "[" );
856 expr
->WriteExpr(stream
);
859 fprintf( stream
, ", " );
861 fprintf( stream
, "]" );
866 case wxExprNull
: break;
871 * wxExpr 'database' (list of expressions)
874 IMPLEMENT_DYNAMIC_CLASS(wxExprDatabase
, wxList
)
876 wxExprDatabase::wxExprDatabase(wxExprErrorHandler handler
)
880 currentwxExprErrorHandler
= handler
;
884 wxExprDatabase::wxExprDatabase(wxExprType type
, const wxString
& attribute
, int size
,
885 wxExprErrorHandler handler
)
888 attribute_to_hash
= attribute
;
889 if (type
== wxExprString
)
890 hash_table
= new wxHashTable(wxKEY_STRING
, size
);
891 else if (type
== wxExprInteger
)
892 hash_table
= new wxHashTable(wxKEY_INTEGER
, size
);
893 else hash_table
= NULL
;
895 currentwxExprErrorHandler
= handler
;
899 wxExprDatabase::~wxExprDatabase(void)
906 void wxExprDatabase::BeginFind(void) // Initialise a search
911 wxExpr
*wxExprDatabase::FindClause(long id
) // Find a term based on an integer id attribute
912 // e.g. node(id=23, type=rectangle, ....).
914 wxExpr
*found
= NULL
;
915 while (position
&& !found
)
917 wxExpr
*term
= (wxExpr
*)position
->Data();
919 if (term
->Type() == wxExprList
)
921 wxExpr
*value
= term
->AttributeValue("id");
922 if (value
->Type() == wxExprInteger
&& value
->IntegerValue() == id
)
925 position
= position
->Next();
930 // Find on basis of attribute/value pairs, e.g. type=rectangle
931 wxExpr
*wxExprDatabase::FindClause(const wxString
& word
, const wxString
& val
)
933 wxExpr
*found
= NULL
;
934 while (position
&& !found
)
936 wxExpr
*term
= (wxExpr
*)position
->Data();
938 if (term
->Type() == wxExprList
)
940 wxExpr
*value
= term
->AttributeValue(word
);
941 if ((value
->Type() == wxExprWord
&& value
->WordValue() == val
) ||
942 (value
->Type() == wxExprString
&& value
->StringValue() == val
))
945 position
= position
->Next();
950 wxExpr
*wxExprDatabase::FindClause(const wxString
& word
, long val
)
952 wxExpr
*found
= NULL
;
953 while (position
&& !found
)
955 wxExpr
*term
= (wxExpr
*)position
->Data();
957 if (term
->Type() == wxExprList
)
959 wxExpr
*value
= term
->AttributeValue(word
);
960 if ((value
->Type() == wxExprInteger
) && (value
->IntegerValue() == val
))
963 position
= position
->Next();
968 wxExpr
*wxExprDatabase::FindClause(const wxString
& word
, double val
)
970 wxExpr
*found
= NULL
;
971 while (position
&& !found
)
973 wxExpr
*term
= (wxExpr
*)position
->Data();
975 if (term
->Type() == wxExprList
)
977 wxExpr
*value
= term
->AttributeValue(word
);
978 if ((value
->Type() == wxExprReal
) && (value
->RealValue() == val
))
981 position
= position
->Next();
986 wxExpr
*wxExprDatabase::FindClauseByFunctor(const wxString
& functor
)
988 wxExpr
*found
= NULL
;
989 while (position
&& !found
)
991 wxExpr
*term
= (wxExpr
*)position
->Data();
993 if (term
->Type() == wxExprList
)
995 if (term
->Functor() == functor
)
998 position
= position
->Next();
1003 // If hashing is on, must store in hash table too
1004 void wxExprDatabase::Append(wxExpr
*clause
)
1006 wxList::Append((wxObject
*)clause
);
1009 wxString
functor(clause
->Functor());
1010 wxExpr
*expr
= clause
->AttributeValue(attribute_to_hash
);
1013 long functor_key
= hash_table
->MakeKey(WXSTRINGCAST functor
);
1015 if (expr
&& expr
->Type() == wxExprString
)
1017 value_key
= hash_table
->MakeKey(WXSTRINGCAST expr
->StringValue());
1018 hash_table
->Put(functor_key
+ value_key
, WXSTRINGCAST expr
->StringValue(), (wxObject
*)clause
);
1020 else if (expr
&& expr
->Type() == wxExprInteger
)
1022 value_key
= expr
->IntegerValue();
1023 hash_table
->Put(functor_key
+ value_key
, expr
->IntegerValue(), (wxObject
*)clause
);
1030 wxExpr
*wxExprDatabase::HashFind(const wxString
& functor
, long value
) const
1032 long key
= hash_table
->MakeKey(WXSTRINGCAST functor
) + value
;
1034 // The key alone isn't guaranteed to be unique:
1035 // must supply value too. Let's assume the value of the
1036 // id is going to be reasonably unique.
1037 return (wxExpr
*)hash_table
->Get(key
, value
);
1040 wxExpr
*wxExprDatabase::HashFind(const wxString
& functor
, const wxString
& value
) const
1042 long key
= hash_table
->MakeKey(WXSTRINGCAST functor
) + hash_table
->MakeKey(WXSTRINGCAST value
);
1043 return (wxExpr
*)hash_table
->Get(key
, WXSTRINGCAST value
);
1046 void wxExprDatabase::ClearDatabase(void)
1049 wxNode
*node
= First();
1052 wxExpr
*expr
= (wxExpr
*)node
->Data();
1059 hash_table
->Clear();
1062 bool wxExprDatabase::Read(const wxString
& filename
)
1066 FILE *f
= wxFopen(filename
, _T("r"));
1069 thewxExprDatabase
= this;
1076 return (noErrors
== 0);
1084 bool wxExprDatabase::ReadFromString(const wxString
& buffer
)
1087 thewxExprDatabase
= this;
1089 const wxWX2MBbuf buf
= buffer
.mb_str();
1090 LexFromString(wxMBSTRINGCAST buf
);
1093 return (noErrors
== 0);
1096 bool wxExprDatabase::Write(const wxString
& fileName
)
1098 FILE *stream
= wxFopen( fileName
, _T("w+"));
1103 bool success
= Write(stream
);
1108 bool wxExprDatabase::Write(FILE *stream
)
1111 wxNode
*node
= First();
1114 wxExpr
*expr
= (wxExpr
*)node
->Data();
1115 expr
->WriteClause(stream
);
1116 node
= node
->Next();
1118 return (noErrors
== 0);
1121 void add_expr(wxExpr
* expr
)
1123 thewxExprDatabase
->Append(expr
);
1127 bool wxExprIsFunctor(wxExpr
*expr
, const wxString
& functor
)
1129 if (expr
&& (expr
->Type() == wxExprList
))
1131 wxExpr
*first_expr
= expr
->value
.first
;
1133 if (first_expr
&& (first_expr
->Type() == wxExprWord
) &&
1134 (first_expr
->WordValue() == functor
))
1144 * Called from parser
1148 char *wxmake_integer(char *str
)
1150 wxExpr
*x
= new wxExpr(atol(str
));
1155 char *wxmake_real(char *str1
, char *str2
)
1159 sprintf(buf
, "%s.%s", str1
, str2
);
1160 double f
= (double)atof(buf
);
1161 wxExpr
*x
= new wxExpr(f
);
1166 // extern "C" double exp10(double);
1168 char *wxmake_exp(char *str1
, char *str2
)
1170 double mantissa
= (double)atoi(str1
);
1171 double exponent
= (double)atoi(str2
);
1173 double d
= mantissa
* pow(10.0, exponent
);
1175 wxExpr
*x
= new wxExpr(d
);
1180 char *wxmake_exp2(char *str1
, char *str2
, char *str3
)
1184 sprintf(buf
, "%s.%s", str1
, str2
);
1185 double mantissa
= (double)atof(buf
);
1186 double exponent
= (double)atoi(str3
);
1188 double d
= mantissa
* pow(10.0, exponent
);
1190 wxExpr
*x
= new wxExpr(d
);
1195 char *wxmake_word(char *str
)
1197 wxExpr
*x
= new wxExpr(wxExprWord
, str
);
1201 char *wxmake_string(char *str
)
1205 const wxMB2WXbuf sbuf
= wxConvLibc
.cMB2WX(str
);
1207 // str++; /* skip leading quote */
1208 len
= wxStrlen(sbuf
) - 1; /* ignore trailing quote */
1210 s
= new wxChar
[len
+ 1];
1213 for(i
=1; i
<len
; i
++) // 1 since we want to skip leading quote
1215 if (sbuf
[i
] == wxT('\\') && sbuf
[i
+1] == wxT('"'))
1220 else if (sbuf
[i
] == wxT('\\') && sbuf
[i
+1] == wxT('\\'))
1231 wxExpr
*x
= new wxExpr(wxExprString
, s
, FALSE
);
1235 char *proio_cons(char * ccar
, char * ccdr
)
1237 wxExpr
*car
= (wxExpr
*)ccar
;
1238 wxExpr
*cdr
= (wxExpr
*)ccdr
;
1242 cdr
= new wxExpr(wxExprList
);
1249 void process_command(char * cexpr
)
1251 wxExpr
*expr
= (wxExpr
*)cexpr
;
1255 void syntax_error(char *WXUNUSED(s
))
1257 if (currentwxExprErrorHandler
)
1258 (void)(*(currentwxExprErrorHandler
))(WXEXPR_ERROR_SYNTAX
, "syntax error");
1259 if (thewxExprDatabase
) thewxExprDatabase
->noErrors
+= 1;
1264 // char *__cdecl strdup(const char *s)
1265 WXDLLEXPORT
char *strdup(const char *s
)
1267 int len
= strlen(s
);
1268 char *new_s
= (char *)malloc(sizeof(char)*(len
+1));