1. Call to c_func() short-circuited

Error message says bad routine number (-1)

Attempting to use

function Read_File(atom hfile, atom lpBuffer, atom nNumberOfBytesToRead) return c_func(Read_File_id, {lpBuffer, nNumberOfBytesToRead, lpNumberOfBytesRead,0} ) end function

Error message also says:

c_proc/c_func: bad routine number (-1)

see ex.err

Warning: .... call to c_func() might be short-circuited.

As an (84 year-old) electrical engineer, I know quite well what the word "short-circuited" means, but I have no idea what it means in this context.

new topic     » topic index » view message » categorize

2. Re: Call to c_func() short-circuited

Hi

Easier to read using the

<eucode> 
-- eucode 
</eucode> 
 

construct so

function Read_File(atom hfile, atom lpBuffer, atom nNumberOfBytesToRead)  
 
return c_func(Read_File_id, {lpBuffer, nNumberOfBytesToRead, lpNumberOfBytesRead,0} )  
 
end function  

would look like that

so, you're calling a c_func - have you defined it somewhere, would be useful to see that. Also what's the purpose of the function (if it's just to read a file, might read_file() here be appropriate?

an explanation of euphorias definition of short circuiting is here - which I don't really understand how it applies here either!

The more information you give, the more useful solutions you''ll get back

Cheers

Chris

new topic     » goto parent     » topic index » view message » categorize

3. Re: Call to c_func() short-circuited

As Chris said, perhaps you are making the task a lot harder than necessary. Is there a reason one of Euphoria's file functions wouldn't do the same job?

If you must call a C routine:

First of all, which .dll or .so contains the C code you wish to call? Are you loading that with open_dll()?

(1) example:

atom LIB = open_dll("xxx.so")
  -- or LIB = open_dll("xxx.dll") on Windows 
? LIB -- if this prints a -1, the library is invalid or can't be found 

Secondly, has Read_File_id been defined?

(2) example:

atom Read_File_id = define_c_func(LIB,"name_of_the_c_function",{PARAMS},RETURN TYPE)
? Read_File_id -- should be an integer, not 0  

Just guessing from the names of the parameters, it appears that your C function is expecting the first parameter lpBuffer to be a pointer to buffer space you have allocated, which the C function will fill with data read, and the 3rd parameter lpNumberOfBytesRead to be allocated space where the C routine expects to store the result so that you can check it later. Possibly the return type would be a boolean to indicate success or failure?

Without further info, it would be hard to guess if this is correct or to guide you on how to allocate those spaces.

new topic     » goto parent     » topic index » view message » categorize

4. Re: Call to c_func() short-circuited

alrobnett said...

Error message says bad routine number (-1)

As others have said, we need to see the definition of Read_File_id

alrobnett said...

Warning: .... call to c_func() might be short-circuited.

As an (84 year-old) electrical engineer, I know quite well what the word "short-circuited" means, but I have no idea what it means in this context.

It just means the call might not take place. Personally I think it is a useless distraction, and phix does not issue such warnings. You will get that message if you have say

if Read_File_id!=-1 and c_func(Read_File_id,{...})!=0 then 

(assuming !=0 means success) which I would suggest avoiding by do this instead:

if Read_File_id!=-1 then 
    if c_func(Read_File_id,{...})!=0 then 

The warning was introduced in version 2.1, when the behaviour of "and" and "or" changed, over 15 years ago, and I don't think anyone needs it any more.

Pete

new topic     » goto parent     » topic index » view message » categorize

5. Re: Call to c_func() short-circuited

Chris said,

"so, you're calling a c_func - have you defined it somewhere, would be useful to see that. Also what's the purpose of the function (if it's just to read a file, might read_file() here be appropriate?"

I appreciatively reply,

I wrote the code 15 to 20 years ago (when I was only 70) to operate in DOS. I am struggling to rejuvenate the program which was at the time, and will be again, very useful to me. (Confession: I am not a programmer. It is the only thing I ever wrote in Euphoria, but I was delighted with the language.) I am told that Euphoria 4 dos not support DOS. My foggy recollection is that I had to use c functions, presumably because "read_file" was not available then. I would be happy (read ecstatic) to use read_file now, but I see that I will need std/io.e which I am unable to locate. The Standard Library website has not been updated since 2013 and is now devoid of useful information.

Fundamental question: If I am able to find std/io.e, can I use everything in it with Euphoria 3?

Allen

new topic     » goto parent     » topic index » view message » categorize

6. Re: Call to c_func() short-circuited

Presumably, you plan to run this on a newer computer, since you are concerned about not having DOS.

New(er) computers, even up thru Windows 10, will run Euphoria 2 or Euphoria 3 or 4 programs in a terminal (cmd.exe). Despite not having DOS.

So, does your program NEED dos? Unless it is a DOS game or uses graphics, the answer is no. It should run on modern computers in a terminal just fine.

All the std/* libraries were introduced in Eu 4.0, and will be installed when you install Eu.4. The std libraries work only with Eu 4.

The "Standard Library" functions have been incorporated into Eu.4, plus many others.

My advice is - providing you are not still using a 20-year-old computer - to install Euphoria 4.1.0 from the downloads tab here, run a few demo programs to make sure it is working correctly, then try your legacy program. If there are problems, ask here.

One important point to consider: Euphoria has always had functions to read files. Why would you have needed those calls to C routines? That is something even advanced programmers avoid if possible. Odds are that all of those C calls can be eliminated, but we can't know that unless you provide specific information:

Give us the name of the .dll you are linking to - i.e. what's in the open_dll() line. And, if possible, the names of the functions in that .dll that you are calling. The names would be found by searching for lines that have define_c_func or define_c_proc in them.

Given those, I'll bet we can figure this out and get the old program working. Might also be helpful to know what the program is supposed to do!

new topic     » goto parent     » topic index » view message » categorize

7. Re: Call to c_func() short-circuited

Many thanks to all who responded. The c_functions worked fine years ago. I don't know why I wasn't aware that there was a simpler approach. In resurrecting the program, I elected to attempt to avoid learning the intricacies of programming for Windows. It now appears that was a mistake. When I used vDos, I had great difficulty locating all of the necessary files where both ed and ex could find them. ed behaves very strangely, advancing many lines when I press ENTER.

Since it has been asked, the purpose of the program is to enable the creation of a binary tree of specifiable depth. I originally used 20 levels, but conclude that 16 will suit my purpose. Even at 16, the bottom level has a potential width of 32,768 entries. Up, Down, Left, and Right keys facilitate moving through the tree. The screen displayed 6 levels of a sub-tree, in tree fashion, below any selected entry. It uses "peek" into the file buffer to get the requested tree entrees. (That involves some fancy calculations.) The program also enables maintenance functions such as moving a subtree from one location to another in the tree. The code is about 21 pages long. I don't think you want to see it.

I have given up on trying to run DOS on my Windows 10, 64 bit machine. I intend now to convert to EU4. Are there documents or hints regarding making the conversion? If not, I will simply correct errors as I come to them.

Thanks again for you time and consideration.

Allen

new topic     » goto parent     » topic index » view message » categorize

8. Re: Call to c_func() short-circuited

Hi

alrobnett said...

I will simply correct errors as I come to them.

That's the best way! Come back when you get stumped.

121 pages eh? How long's a page?

Cheers

Chris

new topic     » goto parent     » topic index » view message » categorize

9. Re: Call to c_func() short-circuited

Twenty one pages, not 121. It is just short of 1000 lines of code.

new topic     » goto parent     » topic index » view message » categorize

10. Re: Call to c_func() short-circuited

Ah, ok, now I've got my glasses on, I see that. I wrote a veterinary practice management system, and that was few lines of code too, but the great thing about euphoria is that it's so readable and easy to go back to and pick up where you left off.

Cheers

Chris

new topic     » goto parent     » topic index » view message » categorize

11. Re: Call to c_func() short-circuited

alrobnett said...

... I have given up on trying to run DOS on my Windows 10, 64 bit machine. I intend now to convert to EU4. Are there documents or hints regarding making the conversion? If not, I will simply correct errors as I come to them. ...

Most of the old Euphoria 2 functions were brought forward to 3 and to 4, so there won't be too many that require a complete change. Just keep the Eu 4 documentation handy. Bear in mind that your code may contain many user-written routines which can now be replaced by a one-line Eu 4 call. So if you see something complex, ask yourself "exactly what does this do?", and then look thru the Eu docs to see if there isn't a routine already build and tested which can do the same job.

Also, I would take a very hard look at each and every C call, since they are:
A: often a source of weird errors and crashes if you aren't a C guru, and
B: difficult to debug, since there are no rational error messages available.
C: often replaceable with simple easy to understand Eu code.

As for "peeking into the file buffer" - might want to re-think that. Your new computer no doubt has enough memory to handle a huge binary tree as a Euphoria sequence, along with efficient routines for manipulating that sequence.

new topic     » goto parent     » topic index » view message » categorize

12. Re: Call to c_func() short-circuited

[quote irv]

As for "peeking into the file buffer" - might want to re-think that. Your new computer no doubt has enough memory to handle a huge binary tree as a Euphoria sequence, along with efficient routines for manipulating that sequence.

I reply:

Thanks Irv, I will definitely see if I can replace the c_functions.

Regarding Peeking into the file buffer, I like the idea of subscipting a sequence in memory to display and modify parts of the tree.

Thank you very much for taking the time to diagnose my problem and making great suggestions.

Allen

new topic     » goto parent     » topic index » view message » categorize

13. Re: Call to c_func() short-circuited

The code below I translated from: https://www.tutorialspoint.com/data_structures_algorithms/tree_traversal_in_c.htm

Note that the node[DATA] item can be any Euphoria object (sequence or nested sequences), so that any kind of data can be stored there. You just need to select which portion of the data is to be considered in the insert and compare functions. e.g. compare(word[1],node[DATA][1]) if the data item is a sequence such as {"key",{moredata...}}

 
include std/console.e 
include std/text.e 
include std/io.e 
include std/filesys.e 
 
object root = 0 
enum DATA, LEFTCHILD, RIGHTCHILD 
enum PRE, ORD, POST 
 
------------------------------------------------ 
function insert(object node, sequence word) 
------------------------------------------------ 
integer x 
 
if length(node) <= 1 then -- create new node 
    node = {word,{},{}} 
else  
	x = compare(word,node[DATA])  
	 
	if x = 0 then -- reject dupes 
	    return node 
	end if 
 
	if x < 0 then 
	    node[LEFTCHILD] = insert(node[LEFTCHILD], word)  
	else 
	    node[RIGHTCHILD] = insert(node[RIGHTCHILD], word) 
	end if 
 
end if 
	 
return node 
end function 
 
---------------------------------- 
function search(object searchdata) 
---------------------------------- 
object current = root 
 
display("visiting elements:") 
 
while not equal(current[DATA],searchdata) do 
    display("\t[1]",current[DATA])  
    if compare(current[DATA],searchdata) > 0 then 
       current = current[LEFTCHILD] 
    else 
       current = current[RIGHTCHILD] 
    end if 
    if length(current)=0 then 
        return sprintf("%s not found",{searchdata}) 
    end if 
end while 
 
return sprintf("Found %s",{searchdata}) 
    
end function 
 
---------------------------------- 
function find(object searchdata) 
---------------------------------- 
object current = root 
integer steps = 0 
 
while not equal(current[DATA],searchdata) do 
 
    if compare(current[DATA],searchdata) > 0 then 
       current = current[LEFTCHILD] 
    else 
       current = current[RIGHTCHILD] 
    end if 
     
    steps += 1 
     
    if length(current)=0 then 
        return 0 
    end if 
     
    display("\t[1]",{current[DATA]})  
 
end while 
 
return format("Found [] in [] steps",{searchdata,steps}) 
    
end function 
 
global object list = {} 
 
--------------------------------------------------------------- 
procedure transverse(object node, integer ord=ORD) -- recursive 
--------------------------------------------------------------- 
if length(node) = 0 then 
    return -- nothing to print 
end if 
 
if ord = PRE then list &= text:format("[1]\n",node) end if 
transverse(node[LEFTCHILD],ord) 
if ord = ORD then list &= text:format("[1]\n",node) end if 
transverse(node[RIGHTCHILD],ord) 
if ord = POST then list &= text:format("[1]\n",node) end if 
 
end procedure 
 
----------------------------------------------------- 
function transverse_list(object node, integer ord=2) 
----------------------------------------------------- 
list = {} 
transverse(node,ord) 
return list 
end function 
 
------------------------------------------------------------------------------ 
 
object words =  
{"Zap","Barn","App","Job","Foo","Bar","App","Jam", 
 "Jim","Bar","Bla","Bar","Zed","Baz","Fred","Joe"} 
 
for i = 1 to length(words) do 
    root = insert(root,words[i]) 
end for 
 
display(transverse_list(root,ORD)) 
display(find("Joe")) 
 
new topic     » goto parent     » topic index » view message » categorize

Search



Quick Links

User menu

Not signed in.

Misc Menu