PR# 2745 see message
Problem Report Summary
Submitter: cheston
Category: Compiler
Priority: Low
Date: 2001/01/31
Class: Bug
Severity: Non-critical
Number: 2745
Release: 4.5.020
Confidential: No
Status: Analyzed
Responsible:
Environment: Pentium III with Windows 98
Synopsis: see message
Description
I have just finished writing a number of Eiffel projects. In the process of doing this task, a number of problems were encountered. Some of these problems were related to differences between the ISE, Visual Eiffel and SmallEiffel implementations of Eiffel. These are discussed separately. Other problems relate to what appear to be bugs in the ISE Eiffel system, or features that could be designed to be more useful. When you are moving to a new version of Eiffel, version 5.0, this seems like the natural time to clean up some of these difficulties. I am currently using ISE EiffelBench version 4.5.020 on a Pentium III with Windows 98. I was given permission to download a beta version of 5.0 Eiffel. However, I was not able to get it running, and did not receive any assistance from a request for help. As a result, none of these have been tried in version 5. I begin with two problems not previously reported. 1. For the following declaration, the error message given below is reported. node : LINKABLE [INTEGER] a_tuple : TUPLE [like node, like node] ------------------------------------------------------------------------------- Error code: VTAT(1) Error: attribute or function improperly used as anchor for `like' declaration. What to do: make sure that anchor type is neither expanded nor itself anchored. Class: TEST_FEATURES Anchor name: Result Anchor type: TUPLE [like node, like node] ------------------------------------------------------------------------------- Corresponding declarations in Visual Eiffel and SmallEiffel do not report an error. Also, no errors occur for b_tuple : TUPLE [like node] 2. This problem is mentioned in the report on differences between the different versions of Eiffel. It is repeated here, so that it does not get lost in the other standard variations. This is really a problem with ISE's interpretation of the standard. When ISE Eiffel reads an integer from a text file or the console, it also reads subsequent blanks and tabs up to and including the next end-of-line marker. The client may want to know about these blanks, so they should not be discarded before the client has the chance to read them. An example of this phenomenon is given at the end of this report. Note that this behavior is inconsistent with Visual Eiffel and SmallEiffel. The following problems were previously reported, but I have not heard back so I don't know if they have been fixed or they are not regarded as a problem. From my perspective, they are all problems, with some more major than others. 1. Reading numeric values from a PLAIN_TEXT_FILE and from the console perform differently. It seems to me that there are errors in the reading of numeric values from the console. In particular, if several values are placed on a line of a file, file reads will obtain all the values. If several values are placed on a line of input at the console, often only the first one is obtained. Note that in the reading of characters, in both cases all the characters are obtained, although there is a different number of characters for the end of a line. Also, when entering data at the console, if a line is entered which contains either blanks or tabs but no data, then an I/O error is often obtained. In general, when reading a numeric value the Eiffel system will read past blanks and tabs on the first line of console input to reach data on the next line entered, and it will read past new lines until reaching a line containing something, even if the something is just a blank or tab. Such a blank or tab may generate an error, i.e. it will not read past blanks and tabs on subsequent lines. On the other hand, when reading from a file, the system reads past an arbitrary number of blanks, tabs, and new lines to reach data. A project is included at the end to show this problem. 2. The function end_of_file does not seem to work with a RAW_FILE. When several items are written into a RAW_FILE, they are placed one after the other, as would be expected. When they are subsequently read from the file, everything works properly except that end_of_file never becomes true. Presently we are using the file position to test for end of file. While this works, it is not very clean, especially when the system has a BOOLEAN function to test for end of file. This problem is also shown in the classes at the end of this message. 3. In the Windows system, the default location for file `output' in local outfile : PLAIN_TEXT_FILE do !!outfile.make_open_write ("output") is in the W_CODE directory of directory EIFGEN. On a unix system, the default location is the same directory as the ace file. They should be consistent. The unix approach seems much better. Visual Eiffel and SmallEiffel place the output file in the same directory as the root class. 4. When both `and' and `and then' exist in a language, one would expect them to be different. However, they seem to have identical affects in version 4.5. This is also true for `or' and `or else'. This is a problem as a project that works fine in ISE Eiffel can fail in Visual Eiffel and SmallEiffel, as these two systems always evaluate both arguments for `and' and `or'. I believe that ISE Eiffel should also do this. 5. The following features of ELKS 95 are not supported or are different from the ELKS specification. feature to_next_line of FILE It is also missing from PLAIN_TEXT_FILE and CONSOLE, but it is in STD_FILES, the type of io. feature fill of STRING feature insert_character of STRING feature put_substring of STRING 6. When an ARRAY of BIT 5 is declared, the system determines that System recompiled System had to be frozen to include new externals. Background C compilation launched. This is a problem for students who do not have a C compiler associated with Eiffel. There is no problem for ARRAYs or BITs by themselves, but the combination causes the system to attempt to freeze the project. This might be a side effect of some optimization, but it seems an abnormality. Also, BIT N is normally considered to be an expanded type. However, when in an array, it is treated as a reference type. I would also like to mention a request: Presently in the PC version, the default console output is to a fixed sized DOS window. Using Windows 98, I don't know how to get around this problem. For students, it would be much more useful if the output were to a scrollable window that could grow to an arbitrary size. To be useful, this would need to work when students only melt and do not have a C compiler associated with Eiffel. If there is an easy way to fix the problem with the present version of Eiffel, say by some different Windows setting, please let me know so that I can use it and students in my course can use it. I would like to also note that this is the second most frequent complaint about the ISE Eiffel system. The most frequent complaint is about its poor error messages. Students new to Eiffel and not very experienced at programming need better error messages. That was one of the main reasons that Eiffel was never even suggested when a couple years ago we switched our first year course from Delphi to Java. I would really appreciate receiving feedback for these comments. Grant Cheston Department of Computer Science University of Saskatchewan Saskatoon, Sask. Canada S7N 5A9 cheston@cs.usask.ca
To Reproduce
A class `TEST_FEATURES' is given below with creation procedure `make'. There is also a class OBJ used by this class, and a data file by the name `data_file'. In this data file, one of the blank lines should contain several blanks and tabs, and there should be several blanks after the 5 in the line containing 4 and 5. When the project is compiled, it will generate an error for the line defining a_tuple. When it is commented out, the project will compile and run until it generates the run-time error Feature: retrieved (From FILE) Reason: Explicit exception pending Code: 27 (I/O error.) Tag: Retrieve: unable to read type of storable. because end of file was not detected. If in the procedure `test_eof_binary', the -- is removed from the second line of the `until', then it will complete the read of the binary file normally. This seems to indicate an error in the feature end_of_file. After reading the binary file, execution will continue and then it will pause for input. The following lines of data should be entered at the console (with `-' used to represent a blank, `tab ' a tab character, and `empty' to represent an empty line): first line:abc second line:defghi third line:1----2----3 fourth line:---- fifth line:empty sixth line:empty seventh line:---- eight line:----tab tab 5-6-7 ninth line:---- tenth line:abc The output as a result of reading the integers from the console is very strange. Also, for both the console and the binary file, the characters obtained after the 5 do not seem correct. Reading from the file, the blanks after the 5 should be obtained. Reading from the console, the 6 and blanks around it should be obtained. ----------------------------------------------------------------- class TEST_FEATURES create make feature make is local i, x, y : INTEGER c : CHARACTER infile : PLAIN_TEXT_FILE do x := 0; y := 1 if x /= 0 and y/x = 1 then -- Should yield a run-time error end if x = 0 or y/x = 1 then -- Should yield a run-time error end test_eof_binary create infile.make_open_read ("..\..\test_data") from i := 1 until i > 7 loop infile.read_character io.put_string ("%NRead character " + infile.last_character.out) i := i + 1 end infile.read_line from i := 1 until i > 5 loop infile.read_integer io.put_string ("%NRead integer " + infile.last_integer.out) i := i + 1 end infile.read_character io.put_string ("%NCharacters after last read_integer" + infile.last_character.out) infile.read_character io.put_string (infile.last_character.out) infile.read_character io.put_string (infile.last_character.out) io.put_string ("%N") from i := 1 until i > 7 loop io.read_character io.put_string ("%NRead character " + io.last_character.out) i := i + 1 end io.read_line io.put_string ("%N") from i := 1 until i > 5 loop io.read_integer io.put_string ("%NRead integer " + io.last_integer.out) io.put_string ("%N") i := i + 1 end io.read_character io.put_string ("%NCharacters after last read_integer" + io.last_character.out) io.read_character io.put_string (io.last_character.out) io.read_character io.put_string (io.last_character.out) io.read_line end node : LINKABLE [INTEGER] a_tuple : TUPLE [like node, like node] b_tuple : TUPLE [like node] test_eof_binary is local outfile : RAW_FILE obj1 : OBJ eof_pos : INTEGER do create outfile.make_open_write ("..\..\binary_outfile") -- The ..\..\ occur in the preceding line for execution on a PC. create obj1.make(5) outfile.basic_store (obj1) create obj1.make(6) outfile.basic_store (obj1) create obj1.make(7) outfile.basic_store (obj1) eof_pos := outfile.count outfile.close io.put_string ("End of file position " + eof_pos.out + "%N") outfile.open_read from until outfile.end_of_file or outfile.position >= eof_pos loop obj1 ?= obj1.retrieved (outfile) io.put_string ("%N" + obj1.out) io.put_string ("Current position " + outfile.position.out + "%N") end io.put_string ("%NPress enter to continue execution") io.read_line end end ----------------------------------------------------------------------------- class OBJ inherit STORABLE create make feature value : INTEGER make (i:INTEGER) is do value := i end end ---------------------------------------------------------------------------- data_file contents: ----------------------------------------------------------------- abc defghi 1 2 3 4 5 789 10 11 12 13 14 15 ---------------------------------------------------------------------------
Problem Report Interactions
State-Changed-From-To: open-analyzed State-Changed-By: Manu State-Changed-When: Wed Jan 31 14:06:53 PST 2001 State-Changed-Why: Dear Grant, Thanks for your message. I will try to answer all points in different emails. For the moment, I would just like to discuss the issue between and/and then and or/or else. This is indeed the case that in ISE Eiffel and/and then and or/or else do the exact same thing. The semantic as explained in ISE Eiffel is the following. When you write: - and then / or else: the compiler garantees that the second part of the boolean expression will be evaluated only if the first one is true in case of `and then', or if the first one is false in the case of `or else'. - and / or have the following semantic: it is up to the compiler to decide in which order those expression will be evaluated at run-time. ETL does not specify that and/or should evaluate both left and right boolean expression. This is a compiler freedom for optimization. Hope this is helpful,