Euphoria Ticket #694: if statement / namespace / sequence weird bug

Don't know what to call this one, but it is a bit strange.

Ok, so the following program will crash with an "true/false condition needs to be an atom" error, which it shouldn't because the "sum()" expression is an atom.

include std/math.e 
 
object x 
 
x = {0,1,2,3,4} 
 
if sum(x < 1 or x > 3) then 
	? 1 
else 
	? 0 
end if 

The weird thing about it is that it will work if you add a namespace qualifier to the sum function, i.e. math:sum

It also works if you define the sum function locally, or assign the sum to a variable and use that in the if statement instead, or simplify the expression being summed "(x < 1)" by itself works ok, it is only with and or'd or and'd expression that it fails.

Details

Type: Bug Report Severity: Normal Category: Interpreter
Assigned To: mattlewis Status: Fixed Reported Release:
Fixed in SVN #: View VCS: none Milestone: 4.0.4

1. Comment by Insolor Jul 21, 2011

Interesting, the following code works as expected:

function sum(sequence s) 
    atom sum 
    sum = 0 
    for i = 1 to length(s) do 
        sum += s[i] 
    end for 
    return sum 
end function 
 
object x 
 
x = {0,1,2,3,4} 
 
if sum(x < 1 or x > 3) then ? 1 else ? 0 end if

Output:

1

2. Comment by mattlewis Jul 21, 2011

When you don't use a namespace, the parser defers fully resolving the symbol from another file until it can prove which symbol you're really asking for. You could be referring to a function later in the same file, or there could be multiple sum functions defined in various include files. That appears to be the source of this.

It appears that the short circuit operation is kicking in on the or operator, which is obviously incorrect. Here is the output of eudis for the code above:

    13: 109 1000                         # GLOBAL_INIT_CHECK: [x:1000] 
    15: 001 1000 1006 1007               # LESS: [x:1000], [LIT 1:1006] => [_temp_:1007] 
    19: 143 1007 1008 32                 # SC1_OR: [_temp_:1007], [_temp_:1008], 0032 
    23: 109 1000                         # GLOBAL_INIT_CHECK: [x:1000] 
    25: 006 1000 1001 1009               # GREATER: [x:1000], [LIT 3:1001] => [_temp_:1009] 
    29: 144 1009 1008                    # SC2_OR: [_temp_:1009], [_temp_:1008] 
    32: 027 775 1008 1010                # FUNC: [sum:775][_temp_:1008] => [_temp_:1010] 
    36: 208 1007                         # DEREF_TEMP: [_temp_:1007]  
    38: 208 1009                         # DEREF_TEMP: [_temp_:1009]  
    40: 020 1010 48                      # IF: [_temp_:1010] = 0 goto 0048 

When using a namespace (or a function already defined in the same file):

    54: 109 1000                         # GLOBAL_INIT_CHECK: [x:1000] 
    56: 001 1000 1006 1012               # LESS: [x:1000], [LIT 1:1006] => [_temp_:1012] 
    60: 109 1000                         # GLOBAL_INIT_CHECK: [x:1000] 
    62: 006 1000 1001 1013               # GREATER: [x:1000], [LIT 3:1001] => [_temp_:1013] 
    66: 009 1012 1013 1014               # OR: [_temp_:1012], [_temp_:1013] => [_temp_:1014] 
    70: 027 775 1014 1015                # FUNC: [sum:775][_temp_:1014] => [_temp_:1015] 
    74: 208 1012                         # DEREF_TEMP: [_temp_:1012]  
    76: 208 1013                         # DEREF_TEMP: [_temp_:1013]  
    78: 208 1014                         # DEREF_TEMP: [_temp_:1014]  
    80: 020 1015 88                      # IF: [_temp_:1015] = 0 goto 0088 

3. Comment by AndySerpa Jul 21, 2011

Hmmm...this may be related to another problem I've been tracking but haven't nailed down. (Memory leak with certain convoluted function calls via routine_id.) More tests...

4. Comment by mattlewis Jul 21, 2011

I don't think this would cause a memory leak.

5. Comment by AndySerpa Jul 21, 2011

Probably not, but this short-circuiting when it is not supposed to may be causing another weird problem I've been trying to figure out the leak I've been trying to find may be caused by code not being executed the way it is supposed to be. In any case, I'm on the trail of another bug that may or may not be connected. I will make a ticket for it when I can isolate it.

6. Comment by DerekParnell Jul 21, 2011

What happens when you put parenthesis around the expressions? ...

include std/math.e  
object x  
x = {0,1,2,3,4}  
if sum( (x < 1) or (x > 3)) then  
	? 1  
else  
	? 0  
end if  

7. Comment by mattlewis Jul 22, 2011

Parentheses result in the same incorrect behavior, whether around the individual comparisons or the or'ed combination of them. Either way, the short circuiting is kicking in.

8. Comment by mattlewis Jul 24, 2011

See: hg:euphoria/rev/bc676d688d48

changeset: 5074:bc676d688d48 branch: 4.0 parent: 5071:736263b340b0 user: Matt Lewis date: Sun Jul 24 11:20:15 2011 -0400 files: tests/t_fwd.e description:

  • test for ticket 694

9. Comment by mattlewis Jul 24, 2011

See: hg:euphoria/rev/2bdff9a70e17

changeset: 5075:2bdff9a70e17 branch: 4.0 user: Matt Lewis date: Sun Jul 24 11:28:34 2011 -0400 files: source/parser.e description:

  • prevent short circuiting in forward calls
  • fixes ticket 694

10. Comment by mattlewis Jul 24, 2011

See: hg:euphoria/rev/856f9971b80b

changeset: 5076:856f9971b80b branch: 4.0 user: Matt Lewis date: Sun Jul 24 11:29:56 2011 -0400 files: docs/release/4.0.4.txt description:

  • release notes for ticket 694

11. Comment by mattlewis Jul 24, 2011

See: hg:euphoria/rev/79567d7709b9

changeset: 5077:79567d7709b9 parent: 5072:ae9647052d94 parent: 5076:856f9971b80b user: Matt Lewis date: Sun Jul 24 11:35:09 2011 -0400 files: source/parser.e tests/t_fwd.e description:

  • merge fix for ticket 694 into the trunk

12. Comment by mattlewis Jul 24, 2011

See: hg:euphoria/rev/5f4bb227afb5

changeset: 5078:5f4bb227afb5 branch: struct tag: tip parent: 5073:182e436a55cd parent: 5077:79567d7709b9 user: Matt Lewis date: Sun Jul 24 11:46:31 2011 -0400 files: source/parser.e description:

  • merge ticket 694 into struct branch

Search



Quick Links

User menu

Not signed in.

Misc Menu