Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Mike Lewis on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

parse an expression

Status
Not open for further replies.

mathmax

Programmer
Apr 21, 2006
22
FR
Hello,

I would like to parse an expression which is a condition of the CA-Clipper language and then translate it into SQL. Do you think that tools like LEX and YACC could help me to solve my problem? Or do you think there is an other better way?

Here is a translation sample:

("Mart" $ Customers->Name .and. Orders->Price >= 120) .or. Oders->Date = ctod("18/06/08")

will be translated to:

where exists (select 0 from Customers as C, Orders as O where C.Id = O.Customers_Id and (C.Name like "%Mart%" and O.Price >= 120) or O.Date = #18/06/08#)

Thank you in advance,

Mathmax
 
This is a C programming forum. Are you asking how to parse it in C?
 
Parsing a complex string in C is usually pretty painful to do. If you can use a scripting language that supports Regex it might be easier.

Otherwise the sscanf() and sprintf() functions in C are probably the best options for parsing.

If all the input strings are the same format (with the same delimitors between elements) it shouldn't be too hard in C.

Are all the input strings the same format as the sample you provided (where only the data inside the quotes changes and maybe the 120 changes)?
 
No the input string can be very different format. In fact I should be able to parse all valid conditions condition from the Clipper language. What do you think about using flex and bison ?
 
I've never used those, so I can't really say, but most of those UNIX utilities are designed for text parsing, so they'd probably be a better choice than C for this case.
 
Those tools generate .c program that do the parsing. I've some difficulties to compile them.
I got the following error message :
Unresolved external symbol "isatty".
Unresolved external symbol "alloca".

Do you have an idea of the problem ?

Regards,

mathmax
 
Can you post the code that's causing the problems?
(and remember to put [ignore]
Code:
[/ignore] tags around the code.)
 
I can't quite remember but I remember seeing an SQL parser at the back of the O'Reiley lex/yacc book. It may be available electronically.

isatty - just write a simple function to return false.
alloca - some variant of malloc.

Shouldn't be too difficult as long as you can work out the grammar. The problem is trying to avoid right recursion.

If you need to debug it, put a break on the switch statement that looks something like

switch ($1)

When you step into it, it goes into a state machine of some sort. Basically yacc/bison generates the state machine for an LALR parser. Once it finds the handle, it will generate the code.

Another alternative is to do it by recursive descent. If you are not expecting any errors, this is quicker than LALR. Error handling can go very badly wrong in recursive descent but if everything is correct, it will just whizz through.
 
I've included the following header files :

#include <malloc.h>
#include <io.h>

This solved the previous errors but I got a lot of compilation errors with them.

For example this error :

Syntax error; found "yy_proto" expecting ";" on the following line (in the .c file) :

extern int isatty YY_PROTO(( int ));

I found the header files on the web. Maybe I don't have the good version of those files. I suppose they are very common files when programming in c. Is there an address where I can download all the common header file for C-programming?
 
<malloc.h> is a standard header file that should come with every C compiler.
<io.h> should already be on just about every UNIX system.
 
Is io.h a std Unix header? I thought it was a std DOS header. Anyway, doesn't really matter.

The isatty stuff doesn't look right. Do you #include unistd.h? isatty is defined in there (ignore my earlier comment).

This is generated by flex. Check your generated file.
 
Very strange: I tried to compile it with Visual Studio 2008 and I the program compiled successfully although it still don't compile with the xHarbour compiler.

By looking at isatty in the source code, I found this:

#ifdef _CVI_
#define fileno(f) (f->handle)
static int isatty (int x) { return x==0; } /* assume stdin is a tty */
#endif

What does _CVI_ means? Is it a portion of code that is read by the Visual Studio compiler and not the xHarbour compiler? It would explain the fact that xHarbour doesn't have knowledge of isatty.

Should I add an include to unistd.h in a #else section, like this:

#ifdef _CVI_
#define fileno(f) (f->handle)
static int isatty (int x) { return x==0; } /* assume stdin is a tty */
#else
#include unistd.h
#endif

unistd.h is for Windows, isn't it ? I work on Windows.
 
I've tried to include unistd.h, but the xHarbour compiler just says "Error : could not compile", when including this file.

Just now, I was saying that Visual Studio compiled the program successfully. That's true but I get an error as soon as I try to execute it. The error is:

Unable to start the program.
This application has failed to start because the application configuration is incorrect. Review the manifest file for possible errors. Reinstalling the application may fix the problem. For more details, please see the application event log.

In this page ( they said I should have a folder called:
x86_microsoft.vc90.crt_1fc8b3b9a1e18e3b_9.0.21022.8_none_bcb86ed6ac711f91 in C:\WINDOWS\WinSxS
But I haven't a such folder. Do you know where I can download it?
 
xwb said:
Is io.h a std Unix header? I thought it was a std DOS header.
Oops, I think you're right. I haven't needed to use that header in a long time.

mathmax said:
unistd.h is for Windows, isn't it ? I work on Windows.
No, <unistd.h> is a UNIX header. <io.h> is the one you want: You'll probably also need to define this:
Code:
#define isatty   _isatty
Because Microsoft loves putting underscores infront of C functions just to piss people off.
 
Application configuration - you need a config file. It is a new thing in .net based stuff. Real pain because they don't tell you about it. Check up config and .net.

Side by side means you're using two different versions of the same DLL. For instance, you probably built one bit with version 2.8 and another bit with version 2.9.

MS puts underscores in front of C functions which aren't std POSIX. They announced this in 1992 (when the C compiler was still distributed on diskettes) but nobody took any notice until stuff started failing. I'm still finding programs using kbhit instead of _kbhit. Now they just say routines are deprecated.
 
Some notes about VS 2008 troubles with Win32 console apps:
1. Try to compile, link and run the application in Release (not Debug) mode. Usually no problems with failed to start when redistributable RTL dll version used in this case.
2. Check Project properties for Debug configuration: set Generate Manifest Yes in Linker|Manifest File to access Debug version of RTL dll.

See your Yacc/lex for Windows package docs to avoid troubles with _CVI_, isatty et al stuff...
 
I've added a config file but what should I put inside ?

Why am I using two diffetent versions of the same DLL ? How to choose to use just one ?
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top