/C-Shells

C and C++ stuff.

Primary LanguageC++

C-Shells

My exploration with C and C++.

C++ GIF

C shells by the sea shore, buffer overflow by adding more?

Notes + References

Table of Contents:

Sections Description
Links External references
Better Usage Usage mistakes explained and corrected
Tools A list of compilation and debugging tools
Notes A list of notes I've made on C and C++ programming

Refer to the main-args.cpp to test out this explanation.

Global getline() works with C++ std::string objects

std::cin.getline() from <istream> works with classic C strings i.e. pointers to char.

cin reads a word e.g. digits/chars separated by whitespace.

std::getline(std::cin, char a); gets the whole line from user and stores in a.

cin.get(char a, streamsize n);cin.get(); gets the whole line (stores in a), then takes in end-of-line character. Repeat this to get a the next line.

cin.get(char a, streamsize n) gets the whole line (stores in a), but repeating this line gives no more input.

the >> operator of std::istream reads space separated strings

stringstream(): converts strings of digits into ints, floats or doubles. atoi(): Only works on C-style strings (character array and string literals). stoi(): C++ 11 only compatible and works for both C++ strings and C style strings.

One of the shortcuts listed in the above link: sizeof( myArray ) is total number of bytes allocated for that array. sizeof( myArray[0] ) is the number of bytes for one element.

sizeof( myArray ) / sizeof( myArray[0] ) is the number of elements in the array.

e.g. when using a function above/before where it was defined in the script.

e.g. C++ static_cast<int>(x) vs C (int)x

e.g. round(0.5) becomes 1


Mistakes on Usage Explained and Resolved.

When using: #include <fstream>

Suppose you have a file.txt with the following content:

1

Your main.cpp file is of the following:

#include <iostream>
#include <fstream>

int main(int argc, char const *argv[])
{
  std::ifstream input_file( argv[0] );

  while( !input_file.eof() )
  {
    int num;

    //storing value
    std::cin >> num;

    // printing value
    std::cout << num;

  }
}

After compilation, loops happen when:

(1) ./a.out < file.txt (2) ./a.out file.txt

Reasons:

(1) End of File is never reached. cin keeps storing the content from the file, and cout keeps printing onto the terminal. Due to the < file.txt portion, a file is never fed into the program. The reason for this is:

./a.out < file.txt is considered as only 1 argument i.e. ./a.out; Fixing argv[0] to argv[3] does not work because doing < file.txt is being utilised by cin.

(2) End of File is never reached. Although 2 arguments are fed into the program, i.e. ./a.out and file.txt, file file.txt was never opened:

Nothing happens when the program runs, since there was no file opened. Adding a boolean check like with input_file.is_open() could be useful to see if the file was successfully opened.

First, std::ifstream input_file( argv[0] ); should be corrected to std::ifstream input_file( argv[1] );. argv[0] is actually refering to ./a.out so having argv[1] refers to file.txt.

Note: having argv[1] unchanged, will show that the file is opened when using input_file.is_open() because a.out itself is a file.

Second, regardless of whether the above fix was made, the program now waits for a user's input from cin. This loops forever, and will proceed to ask for a user's input forever (only if an int/number was given). If an anything other than a number was given, an infinite/forever loop of zeros will show.

The infinite loop happens, because this program never reaches the end of files argv[1] or argv[0].

The ifstream Object

Use the constructor and let its destuctor do the work of opening and closing the file. source

// if this is done:
std::ifstream input_file( argv[0] );

// Then the following is unnecessary:
//
// close the file when parsing is done
std::ifstream input_file;

input_file.Open(argv[0]);

input_file.close();

Compiler Versions

gcc (GCC) 10.2.1 20200723 (Red Hat 10.2.1-1)

gcc (Ubuntu 5.5.0-12ubuntu1) 5.5.0 20171010

General command to compile:

gcc -Wall filename.c -o filename

Since,

gnu18

GNU dialect of ISO C17 is the default for C code.

Use -std=c99 flag for the C99 standard.

And,

gnu++14

gnu++1y

GNU dialect of -std=c++14 is the default for C++ code. gnu++1y is deprecated.

Debugging Tools

GNU gdb (GDB) Fedora 9.1-6.fc32

GNU gdb (GDB) 8.1

Error encountered during usage on Mac OSX:

Unable to find Mach task port for process-id 7234: (os/kern) failure (0x5). (please check gdb is codesigned - see taskgated(8))

To resolve issue above:

Link to the related Github Issue

  • This more reader friendly, as in not txt file print but the content mentioned in the above link was copied from this.

Similar but for lldb

  • The work around "the bug" that this link is referring to can be found here.

How I resolved this::

Before creating the certificate, check the version of gdb by doing gdb --version.

  • if it is not version 8.0.1, then do the following:
    1. Run brew uninstall gdb, if that doesn't work then do, brew uninstall --force gdb. Doing brew unlink gdb may work instead, look at this discussion.
    2. Now do brew install https://raw.githubusercontent.com/Homebrew/homebrew-core/c3128a5c335bd2fa75ffba9d721e9910134e4644/Formula/gdb.rb.

For more information on the above, refer to this on StackOverFlow.

The following are steps to codesign gdb:

  1. In Keychain Access (toolbar i.e. where system time is displayed), go to Certificate Assistant and Create a Certificate.
  2. Enter a relatable name for this Certificate e.g. "gdb_cert".
  3. Fill in the following and then click create:
  • Identity Type: Self Signed Root
  • Certificate Type: Code Signing
  1. Double click on the Certificate which can be found in "Login" category.
  2. In the popup window, click on the "Trust" arrow and select "Always Trust" when using this Certificate.
  3. Drag this Certificate from the Login category to "System".
  4. Run killall taskgated:
  • if No matching processes belonging to you were found then do ps aux | grep taskgated
  1. Finally run codesign -fs nameofcertificate /usr/local/bin/gdb:
  • To find path location of gdb run which gdb
  • This command does not need to be in the same directory of the Certificate
  1. Restart machine.

This may happen:

(gdb) file a.out \"a.out\": not in executable format: File format not recognized

Do g++ -m32 filename.cpp -g -Wall to resolve, as noted here, existing GDB installed may be the x86_32 version.

valgrind-3.13.0


These are links to a separate README.md.