Thread: iostream problem

  1. #16
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    This all the contents in common.h
    extern int currentLineNumber;
    extern int currentNestingLevel;

    This all the contents in common.cpp
    int currentNestingLevel = 0;
    int currentLineNumber = 0;

    Now you can see why I did not include it in the post, but I did include it in buffer.cpp! Commenting out this include is an error, I actually do include it!
    It's only used in one function.

    I did not know you cannot use namespaces in header files!!! But I also did not try to use it in header files for this project!

    I also made a little test project using fstream: I opened for reading, read, closed, opened for writing, wrote, closed etc and all compiled OK. I even put in "fstream file;" the line that my other project is complaining about and the compiler took that line also. So it can't be the compiler or the project. Something has got to be screwed up with the code of the includes in buffer.cpp.
    Last edited by maxcy; 08-29-2023 at 07:00 PM. Reason: typo

  2. #17
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    The common.h was a mistake, it is in the project. noreplace was used instead of nocreate (deprecated). It's commented out. std::fstream was replaced. All compiles well except a new problem. In CodeBlocks, when one creates a new project, a new main.cpp file, is made by default. After entering in the .h and .cpp files main.cpp is no longer needed so I remove it from the project and go on from there. I've done this several dozens of times before and never had a problem. This time I got an error message about not being able to find main.o! Problem in the makefile I think. So after much monkeying around I finally found where the main.cpp file was still in the project makefile! Got rid of it and now everything compiles and runs!!!!! I still have to go back and fix your recommendation about char* and string. I still have to figure out why std:: namespaces are needed in a header file that uses a library.
    thanks ever so much for your help in getting my endeavor up and running.

  3. #18
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,666
    > I did not know you cannot use namespaces in header files!
    I didn't say you cannot.
    I said it's a supremely BAD idea to do so.

    > I still have to figure out why std:: namespaces are needed in a header file that uses a library.
    Because everything in modern C++ is in one namespace or another.

    Here is an example program using namespaces.
    Code:
    #include <iostream>
    #include <fstream>
    
    void foo ( ) {
        std::cout << "This is foo\n";
    }
    
    namespace cprog {
    
    int bar ( ) {
        return 42;
    }
    
    }
    
    int main ( ) {
        std::fstream is;        // fstream is in the std:: namespace
        foo();                  // foo is in the global namespace
        int x = cprog::bar();   // bar is in the cprog namespace
        std::cout << "Bar=" << x << "\n";
    }
    And the same with using namespace
    Code:
    #include <iostream>
    #include <fstream>
    using namespace std;
    
    void foo ( ) {
        cout << "This is foo\n";
    }
    
    namespace cprog {
    
    int bar ( ) {
        return 42;
    }
    
    }
    
    int main ( ) {
        fstream is;             // fstream is in the std:: namespace
        foo();                  // foo is in the global namespace
        int x = cprog::bar();   // bar is in the cprog namespace
        cout << "Bar=" << x << "\n";
    }
    In short, "using namespace std;" is a lazy one line sop to make ancient C++ programs somewhat usable in modern C++ (when everything moved from the global namespace to the std namespace).

    While you're writing toy programs that depend only on the standard library, it's somewhat harmless.

    But when you get to writing code importing namespaces from several external libraries, then knowing how to use namespaces properly becomes far more important.
    So if you want to save some future grief, stop being lazy and learn to write std:: in front of all the references to the standard library.

    There is a half-way house approach.
    Code:
    #include <iostream>
    #include <fstream>
    
    // I use std::cout a lot, so just make this one thing a bit
    // easier on the eye and the fingers.
    // Everything else would need to be qualified with std::
    using std::cout;
    
    void foo ( ) {
        cout << "This is foo\n";
    }
    
    namespace cprog {
    
    int bar ( ) {
        return 42;
    }
    
    }
    
    int main ( ) {
        std::fstream is;        // fstream is in the std:: namespace
        foo();                  // foo is in the global namespace
        int x = cprog::bar();   // bar is in the cprog namespace
        cout << "Bar=" << x << "\n";
    }
    > After entering in the .h and .cpp files main.cpp is no longer needed so I remove it ...
    Make sure to save the project.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  4. #19
    Registered User
    Join Date
    Aug 2023
    Posts
    45

    Talking opening a fstream file

    Code:
    TTextInBuffer::TTextInBuffer(const char *pInputFileName, TAbortCode ac)
        : pFileName(new char[strlen(pInputFileName) + 1])
    {
        //--Copy the input file name.
        strcpy(pFileName, pInputFileName);
    
    //--Open the input file.  Abort if failed.
        file.open(pFileName, std::ios::in /* | std::ios::noreplace */ );  // +=+ file is declared in buffer.h per discussion(std::fstream file)
        if (!file.good())           // +=+ file.good() is not working!!!
            AbortTranslation(ac);   // +=+ this is exiting the program!!!
    }
    When I run this is in the debugger, pFileName comes from argv[1] and the watch shows the intended file from the command line. 'noreplace' has been commented out, but the code skips to the AbortTranslation line and exits! If I take out the last 2 lines, the code runs, but all I get are empty entries from the not opened file! So the only thing left is the file.open line and the only thing that I changed there was to eliminate the 'noreplace'! Why doesn't the file open?

    I do have the most recent compiler, version 13.1.0) and that should allow -std=c++23 but I have not figured out how to do this in either CodeBlocks or DevC++!

    Your string idea was nice but my code, an enum of strings, didn't seem feasible so I just changed char * to const char * and the compiler was very happy.
    maxcy
    Last edited by maxcy; 09-01-2023 at 12:00 PM. Reason: typo

  5. #20
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,666
    Try getting more information, rather than saying "it doesn't work".

    Code:
        if (!file.good()) {
            std::cerr << "Could not open >" << pFileName << "<\n";
            std::cerr << "Error=" << std::strerror(errno) << "\n";  // #include <cerrno>
            AbortTranslation(ac);   // +=+ this is exiting the program!!!
    Note the use of printing >< immediately around the filename, as this helps spot things like stray spaces and/or newlines in whatever you think the filename is.

    > When I run this is in the debugger, pFileName comes from argv[1]
    Bear in mind that what the program considers to be "the current directory" can differ depending on how you invoke the program.
    - running in the debugger
    - running from an IDE menu 'run'
    - running from an external command line.

    The file may exist, but you could be looking in the wrong place.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  6. #21
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    Code:
       //--Open the input file.  Abort if failed.
        file.open(pFileName, std::ios::in /* | std::ios::noreplace */ );  // +=+ file is declared in buffer.h
        if (!file.good())           // +=+ file.ios::good() is not working!!!
            AbortTranslation(ac);   // +=+ this is exiting the program!!!
    }
    file is declared: std::fstream file; per previous discussion! good() is declared in ios:: namespace per online documentation and certainly not in the fstream namespace! Using file.ios::good() (ios namespace) doesn't work and neither does file.std::ios::good() is worst obviously (confused namespaces)! The good part is that the AbortTranslation(ac) does work! So why is good() all screwed up???
    maxcy

  7. #22
    Registered User
    Join Date
    Aug 2023
    Posts
    45

    Exclamation file will not open

    Code:
        file.open (pFileName, std::fstream::in);
        if (file.fail())
        {
           cout << "*pFileName:  ";
           for ( int i =0; i <= 7; i++) {
                cout << pFileName[i];  // name is good
           }
           cout << endl;
           std::cerr << "Could not open >" << pFileName << "<\n"; // so is this
           std::cerr << "Error=" << std::strerror(errno) << "\n";  // #include <cerrno>
           AbortTranslation(ac);
           file.clear();
        }
    New updated test code above: results are
    *pFileName: WOLF.PAS
    could not open >WOLF.PAS<
    Error=no such file or directory
    *** Fatal translator error: failed to open source file

    I even copied the WOLF.PAS file into the same directory as the exe
    file was in.

    I've added exec file parameters many times before in Code::Blocks and DevC++ and never had any problems running the exe with filenames.

    This is strange!!!!

  8. #23
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,666
    Find out where it's looking
    _getcwd, _wgetcwd | Microsoft Learn
    getcwd(3) - Linux manual page

    The current directory isn't necessarily where the executable is.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  9. #24
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    Code:
    
    #include <direct.h> // _getcwd
    #include <stdlib.h> // free, perror
    #include <stdio.h>  // printf
    #include <string.h> // strlen
    
    
    main( void )
    {
       char* buffer;
    
    
       // Get the current working directory:
       if ( (buffer = _getcwd( NULL, 0 )) == NULL )
          perror( "_getcwd error" );
       else
       {
          printf( "%s \nLength: %zu\n", buffer, strlen(buffer) );
          free(buffer);
       }
    }
    I put this little program into the problem .exe directory and ran the exe file in that directory. It shows the same directory as the .exe file. Like I said, I've done this very same thing dozens of times with all the other projects.

  10. #25
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,666
    Good, now do the same thing in the error path when it can't find the file.

    The current directory isn't a fixed thing set at the start of the program. If some other part of your code does a chdir (that you don't know about, or you forgot about), then you can easily be looking in the wrong place.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  11. #26
    Registered User
    Join Date
    Aug 2023
    Posts
    45

    Question error path

    I forgot to mention this but when I am in the debugger watch, I can see argv[1] shows the file name of the file that I am trying to open. How would I find the error path? Why all of a sudden in this one project does this happen. and never in all the others.
    maxcy

  12. #27
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,666
    Code:
    file.open (pFileName, std::fstream::in);
    if (file.fail())
    {
       // This is the error path (through the code)
       cout << "*pFileName:  ";
       for ( int i =0; i <= 7; i++) {
            cout << pFileName[i];  // name is good
       }
       cout << endl;
       std::cerr << "Could not open >" << pFileName << "<\n"; // so is this
       std::cerr << "Error=" << std::strerror(errno) << "\n";  // #include <cerrno>
       AbortTranslation(ac);
       file.clear();
    }
    Put the getcwd code here also, to find out in what directory it tried to find the file.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  13. #28
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    Quote Originally Posted by maxcy View Post
    Code:
        file.open (pFileName, std::fstream::in);
        if (file.fail())
        {
           cout << "*pFileName:  ";
           for ( int i =0; i <= 7; i++) {
                cout << pFileName[i];  // name is good
           }
           cout << endl;
           std::cerr << "Could not open >" << pFileName << "<\n"; // so is this
           std::cerr << "Error=" << std::strerror(errno) << "\n";  // #include <cerrno>
           AbortTranslation(ac);
           file.clear();
        }
    New updated test code above: results are
    *pFileName: WOLF.PAS
    could not open >WOLF.PAS<
    Error=no such file or directory
    *** Fatal translator error: failed to open source file

    I even copied the WOLF.PAS file into the same directory as the exe
    file was in.

    I've added exec file parameters many times before in Code::Blocks and DevC++ and never had any problems running the exe with filenames.

    This is strange!!!!
    Been on hiatus for a week! In the above loop i <= 7 I believe should be i <= strlen(*pFileName) or else whitespace after the file name will not be found!
    maxcy

  14. #29
    Registered User
    Join Date
    Aug 2023
    Posts
    45
    When I used _getcwd in the exe folders I got the same cwd. When I used _getcwd in the problem project the cwd pointed to the root directory of the project. So I copied the argv file into the root folder and now everything is working!!!! This is the way it works using CodeBlocks. Working with older code may be a little tedious, but it does teach a great deal about learning a lot of things that are not covered in books, only hands on experience helps here.
    Thanks for all the great help!!! maxcy

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. IOSTREAM problem
    By joan in forum C++ Programming
    Replies: 13
    Last Post: 12-01-2006, 02:56 PM
  2. Problem during compile (iostream.h error)
    By JoJo in forum C Programming
    Replies: 4
    Last Post: 04-29-2003, 06:58 PM
  3. iostream problem. Help! :P
    By skyvoyager in forum C++ Programming
    Replies: 4
    Last Post: 08-05-2002, 10:14 PM
  4. iostream.h help???
    By chaoticseedalpha in forum C++ Programming
    Replies: 10
    Last Post: 01-29-2002, 10:12 AM
  5. Iostream
    By Staticman in forum Game Programming
    Replies: 2
    Last Post: 10-16-2001, 03:48 PM

Tags for this Thread