1. Functions & Procedure runing stak

Hello everybody, I search for the name of the euphoria sequence (if there is) containing the stack of nested functions or procedures running in my program (by their name or routine Id) - Any help would be greatly appreciated !

new topic     » topic index » view message » categorize

2. Re: Functions & Procedure runing stak

clkeriolet said...

Hello everybody, I search for the name of the euphoria sequence (if there is) containing the stack of nested functions or procedures running in my program (by their name or routine Id) - Any help would be greatly appreciated !

I am not sure if this routine is what you are asking for. Perhaps it will help.

-- 
--- file qindex.ex  by Phil F. 
---     (lists global & local routines from Euphoria source files --- 
---     with line numbers)   -- 
--- usage: eui qindex.ex Eusourcefile   -- 
---   or:  eui qindex.ex Eusourcefile > keepme.txt    -- 
 
-- modified to list public and export routines by Kenneth Rhodes 
 
include std/io.e 
integer fn, ch, found, ct, outdev 
sequence f, test, params, num 
object l 
outdev = 1 -- >> usually to console -- 
params = command_line() 
if length(params) < 3 then 
	puts(1,"Usage: eui qindex.ex sourcefile > [optional] keepme.txt\n") 
end if 
f = params[3] 
fn = open(f,"r") 
if fn < 0 then 
	puts(1, "Sorry, could not open " & f & '\n') 
	abort(0) 
end if 
 
ct = 0 
puts(outdev, "\n---  " & f & "  ---\n") 
found = 0 
while 1 do 
	l = gets(fn) 
	ct += 1 
	if atom(l) then exit end if --- end of file -- 
	if length(l) < 8 then continue end if --- "function" won't fit  -- 
	if length(l) > 100 then 
		l = l[1..100] & '\n' 
	end if 
	test = "" 
	for i = 1 to length(l) do 
		ch = l[i] 
		if not find(ch, " \t") then --- 'non-spaces' only -- 
			test &= ch 
			if equal(test, "--") then 
				continue 
			elsif find(test, {"global","public", "export"}) then   
				test = ""  --- skip -- 
                        elsif find(test, {"procedure", "function"}) then 
				num = sprintf("%d: ", ct) 
				puts(outdev, num & l) 
				found += 1 
			elsif length(test) > 9 then -- seen enough! -- 
				continue 
			end if 
		end if 
	end for 
end while 
if found = 0 then 
	puts(outdev, "None found\n") 
end if 
puts(outdev,"-----------------\n") 
close(fn) 
new topic     » goto parent     » topic index » view message » categorize

3. Re: Functions & Procedure runing stak

No. You could write your own by combining fork from C and crash, though.

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

4. Re: Functions & Procedure runing stak

Perhaps you could use profile for that. Just add "with profile" at the top of your program (without quotes). It will give you a program listing with the number of times each line is executed.

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

5. Re: Functions & Procedure runing stak

In Euphoria 4.1, you can get the current call stack at any time.

 
include std/io.e 
include std/sequence.e 
include euphoria/debug/debug.e 
 
constant CS_FORMAT_STRING = "routine '%s' called from %s:%d\n" 
 
procedure show_call_stack( integer start = 1 ) 
     
    sequence cs = call_stack() 
     
    if start <= length( cs ) then 
        cs = cs[start..$] 
    end if 
     
    for i = 1 to length( cs ) do 
         
        object routine_name, file_name, line_no 
        {routine_name,file_name,line_no} = cs[i] 
         
        if i > 1 then puts( STDOUT, ">>> " ) end if 
        printf( STDOUT, CS_FORMAT_STRING, {routine_name,file_name,line_no} ) 
         
    end for 
     
end procedure 
 
procedure main() 
     
    -- skip first line, which is the 
    -- call to 'call_stack()' itself 
    show_call_stack( 2 ) 
     
end procedure 
 
main() 

D:\Greg\Documents\Euphoria\Testing> eui call_stack.ex 
routine 'show_call_stack' called from D:\Greg\Documents\Euphoria\Testing\call_stack.ex:10 
>>> routine '<TopLevel>' called from D:\Greg\Documents\Euphoria\Testing\call_stack.ex:37 

Fun fact: main() got inlined, so it doesn't show up in the call stack. If you change its declaration to without inline procedure main() then it will show up in the call stack.

D:\Greg\Documents\Euphoria\Testing>eui call_stack.ex 
routine 'show_call_stack' called from D:\Greg\Documents\Euphoria\Testing\call_stack.ex:10 
>>> routine 'main' called from D:\Greg\Documents\Euphoria\Testing\call_stack.ex:35 
>>> routine '<TopLevel>' called from D:\Greg\Documents\Euphoria\Testing\call_stack.ex:37 

There's also functionality to use your own external debugger, but it doesn't seem well documented, so I'm still trying to figure out how to use it. I will provide a proper example when I do (but don't look for that any time soon).

-Greg

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

6. Re: Functions & Procedure runing stak

Not sure if this is what you meant, but (for Phix) see http://rosettacode.org/wiki/Stack_traces#Phix

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

7. Re: Functions & Procedure runing stak

Thanks Greg for your example, The idea behind my need for that stack is that in my program I have procedures which should behave in a different maner depending from where (with path) they are called. I tried your example, and nothing appear on my screen, I added a "puts(1,"\n\nPress Enter...") gets(0)" at the end of your program, but again nothing appear. I had to generate an error at the end of the main and I got an ouput similar to yours. But it works only one time !, I have to restart my computer to make it work again one time ! It seems like it runs in a debugg mode that affects normal execution (printf and puts not working) ! Do you have an idea about what is going on ?

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

8. Re: Functions & Procedure runing stak

clkeriolet said...

Thanks Greg for your example, The idea behind my need for that stack is that in my program I have procedures which should behave in a different maner depending from where (with path) they are called. I tried your example, and nothing appear on my screen, I added a "puts(1,"\n\nPress Enter...") gets(0)" at the end of your program, but again nothing appear. I had to generate an error at the end of the main and I got an ouput similar to yours. But it works only one time !, I have to restart my computer to make it work again one time ! It seems like it runs in a debugg mode that affects normal execution (printf and puts not working) ! Do you have an idea about what is going on ?

Hi,

I don't know what your use case is but have you considered just using an extra parameter (possibly optional) in the routine calls to indicate 'where' ?

Spock

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

9. Re: Functions & Procedure runing stak

To Spock : yes indeed, it could be a solution, but very heavy :

1-I know that the system must have somewhere that stack to execute correctly a program. So why wheighting my software for something that aready exits ?

2-In that software that's not only the "Where" but more the "How" ie the path that I need. If you consider an average path of ten nested procedures/function choosed among hundreds of possible procedures/functions, then it makes a very big number of combinations !. It's much easy and lighter to analyse the path directly .

3- I cannot forecast all the possibles combinations, so manage an extra parameter, as you suggest, seems difficult. But the path give me plenty of data I can use to tell what my procedure should best prefer and Do !

Many thanks for your suggestion.

regards

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

10. Re: Functions & Procedure runing stak

It seems that this stack subject is an old one with similar results : https://openeuphoria.org/forum/125837.wc#125837

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

11. Re: Functions & Procedure runing stak

Based on what you've explained so far, I really think that maintaining your own path stack is going to be better than contstantly examining the internal call stack. The call stack is really only provided for debugging purposes, which is why it lives in euphoria/debug. If you could, please provide an example of what you're trying to accomplish, I'd like to learn more and hopefully suggest a better solution.

-Greg

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

12. Re: Functions & Procedure runing stak

Hi Greg, I hope you had a good Sunday, mine was to make some tests, so the delay to answer you !

C is not my cup of tea, so I checked two solutions with Eu :

1- I made two functions, the first one increases the stack by the name of the procedure and is called at the entry to all of the concerned procedures. The second is called at the end of the procedures and decreases the stack. As a result at any point of time I have acces to that stack. It works well but as I thought, it cost me 50% more in execucion time !

2- The second solution I tested is similar, I avoided to create the two functions, and I put the short code of them directly in the procedures. So I saved some execution time with a 35% increase.

In my project (acquisition&learning&understanding of natural/human language). I have a few procedures that need to know from where(with the path) among hundreds they have been called, so I can take proper action.

As a simple example, it can be used for an error handling procedure that needs to reset only specific variables depending of the procedures initiated but not terminated correctly. But that stack may also be very usefull to write less hierarchically predetermined code.

It would be great if it was not so time consuming. I believe that stack must exist somewhere in the system don't you think ? And It has to be compilabe !

regards

- Chris

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

13. Re: Functions & Procedure runing stak

clkeriolet said...

I have a few procedures that need to know from where(with the path) among hundreds they have been called, so I can take proper action.

The traditional approach is to supply a parameter to determine that sort of thing, for example

enum MOVE, COPY, DELETE 
procedure process_file(integer action, ...) 
   ... 
end procedure 
 
procedure move_file(...) 
   process_file(MOVE,...) 
end procedure 
 
procedure copy_file(...) 
   process_file(COPY,...) 
end procedure 
 
procedure delete_file(...) 
   process_file(DELETE,...) 
end procedure 

rather than have process_file try to figure out which routine it was called from.

Pete

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

Search



Quick Links

User menu

Not signed in.

Misc Menu