MacLochlainns Weblog

Michael McLaughlin's Technical Blog

Site Admin

Archive for the ‘C Programming’ tag

Quick C How-to add .h

without comments

Somebody wanted a quick example of using a user-defined header file for a constant value. While I think there a lot of examples on the Internet already, here’s quick example.

You can define a header (or global.h) file in the local directory with the value of pi, like this:

1
2
// A global header file for constants.
double pi = 3.1415926535;

Then, you can write a little circle.c program like so:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#include <stdio.h>
#include "global.h"
 
int main() {
  int r;
  double area;
 
  // Get the radius.
  printf("Enter a radius in inches: ");
  scanf("%i",&r);
 
  // Calculate the area of a circle.
  area = pi * (r * r);
 
  // Print the radius and circle area.
  printf("Area of a %d inch circle is %lf square inches!\n",r,area);
  return(0); }

The local global.h file is enclosed in double quotes rather than less than and great than symbols. You can compile circle.c like this on Linux, provided both files are in the same directory:

gcc -o circle circle.c

According to the gcc-documentation, the priority for include <> is, on a “standard Unix system”, as follows:

/usr/local/include
libdir/gcc/target/version/include
/usr/target/include
/usr/include

You should chmod the circle file as executable and then you can run it like so:

./circle

You’ll see more or less the following:

Enter a radius in inches: 3
Area of a 3 inch circle is 28.274334 square inches!

As always, I hope the example helps those looking for a starting point.

Written by maclochlainn

January 26th, 2020 at 12:49 am

Posted in C,C/C++ Programming,Linux,Unix

Tagged with

C Shared Libraries

without comments

I wrote a shared C library example to demonstrate external procedures in the Oracle Database 11g PL/SQL Programming book. I also reused the same example to demonstrate Oracle’s external procedures in the Oracle Database 12c PL/SQL Advanced Programming Techniques book last year. The example uses a C Shared Library but a PL/SQL wrapper and PL/SQL test case.

One of my students asked me to simplify the unit test case example by writing the complete unit test in the C Progamming Language. The student request seemed like a good idea, and while poking around on the web it appears there’s a strong case for a set of simple shared C library examples. This blog post isn’t meant to replace the C Programming web site and C Programming Tutorial web site, which I recommend as a great reference point.

Like most things, the best place to start is with basics of C programming because some readers may be very new to C programming. I’ll start with basic standalone programs and how to use the gcc compiler before showing you how to use shared C libraries.

The most basic program is a hello.c program that serves as a “Hello World!” program:

1
2
3
4
5
#include <stdio.h>
 
int main() {
  printf("Hello World!\n");
  return(0); }

Assuming you put the C source files in a src subdirectory and the executable files in a bin subdirectory. You compile the program with the gcc program from the parent directory of the src and bin subdirectories, as follows:

gcc -o bin/hello src/hello.c

Then, you execute the hello executable program from the parent directory as follows:

bin/hello

It prints:

Hello World!

You can modify the basic Hello World! program to accept a single input word, like this hello_whom.c program:

1
2
3
4
5
6
7
8
9
10
11
12
#include <stdio.h>
 
/* The executable main method. */
int main() {
  // Declare a character array to hold an input value.
  char whom[30];
 
  /* Print a question and read a string input. */
  printf("Who are you? ");
  scanf("%s", whom);
  printf("Hello %s!\n", whom);
  return(0); }

You can compile the hello_whom.c program as follows:

gcc -o bin/hello_whom src/hello_whom.c

Then, you execute the hello_whom executable program from the parent directory as follows:

bin/hello_whom
Who are you? Stuart

It prints:

Hello Stuart!

Alternatively, you can modify the hello_whom.c program to accept a stream of text, like the following hello_string.c program:

1
2
3
4
5
6
7
8
9
10
11
12
#include <stdio.h>
 
/* The executable main method. */
int main() {
  // Declare a character array to hold an input name.
  char phrase[4000];
 
  /* Print a question and read a string input. */
  printf("Hello? ");
  scanf("%[^\n]%*c", phrase);
  printf("Hello %s!\n", phrase);
  return(0); }

The [] is the scan set character. The [^\n] on line 10 defines the input as not a newline with a white space, and the %*c reads the newline character from the input buffer. After you compile the program you can call it like this:

bin/hello_string
Hello? there, it reads like a C++ stream

It would print:

Hello there, it reads like a C++ stream!

These example, like the previous examples, assume the source files are in a src subdirectory and the executable files are in the bin subdirectory. All compilation commands are run from the parent directory of the src and bin subdirectories.

The first example puts everything into a single writingstr.c file. It defines a writestr() function prototype before the main() function and the writestr() function after the main() function.

The code follows below:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
#include <stdio.h>
 
/* Declare two integer variables. */
char path[255], message[4000];
 
/* Define a prototype for the writestr() function. */
void writestr(char *path, char *message);
 
/* The executable main method. */
int main() {
  printf("Enter file name and message: ");
  scanf("%s %[^\n]%*c", &path, &message);
  printf("File name:    %s\n", path);
  printf("File content: %s\n", message);
  writestr(path, message);
  return(0); }
 
void writestr(char *path, char *message) {
  FILE *file_name;
  file_name = fopen(path,"w");
  fprintf(file_name,"%s\n",message);
  fclose(file_name); }

You can compile the writingstr.c function with the following syntax:

gcc -o bin/writingstr src/writingstr.c

You can run the writingstr executable file with the following syntax:

bin/writingstr
Enter file name and message: /home/student/Code/c/test.txt A string for a file.
File name:    /home/student/Code/c/test.txt
File content: A string for a file.

You’ll find a test.txt file written to the /home/student/Code/C directory. The file contains only the single sentence fragment entered above.

Now, let’s create a writestr.h header file, a writestr.c shared object file, and a main.c testing file. You should note a pattern between the self-contained code and the approach for using shared libraries. The prototype of the writestr() function becomes the definition of the writestr.h file, and the implementation of the writestr() function becomes the writestr.so shared library.

The main.c file contains the only the main() function from the writingstr.c file. The main() function uses the standard scanf() function to read a fully qualified file name (also known as a path) as a string and then a text stream for the content of the file.

You define the writestr.h header file as:

1
2
3
4
5
6
#ifndef writestr_h__
#define writestr_h__
 
extern void writestr(char *path, char *message);
 
#endif

You define the writestr.c shared library, which differs from the example in the book. The difference is the #include statement of the writestr.h header file. The source code follows:

1
2
3
4
5
6
7
8
#include <stdio.h>
#include "writestr.h"
 
void writestr(char *path, char *message) {
  FILE *file_name;
  file_name = fopen(path,"w");
  fprintf(file_name,"%s\n",message);
  fclose(file_name); }

You define the main.c testing program as:

1
2
3
4
5
6
7
8
9
10
11
12
#include <stdio.h>
#include "writestr.h"
 
/* Declare two integer variables. */
char path[255], message[4000];
 
/* The executable main method. */
int main() {
  printf("Enter file name and message: ");
  scanf("%s %[^\n]%*c", &path, &message);
  writestr(path, message);
  return(0); }

Before you begin the process to compile these, you should create an environment file that sets the $LD_LIBRARY_PATH environment variable or add it to your .bashrc file. You should point the $LD_LIBRARY_PATH variable to the directory where you’ve put your shared libraries.

# Set the LD_LIBRARY_PATH environment variable.
export LD_LIBRARY_PATH=/home/student/Code/c/trylib/libfile

With programs defined, you need to first compile the writestr.c shared library first. You use the following syntax from the parent directory of the src and bin subdirectories.

gcc -shared -fPIC -o bin/writestr.so src/writestr.c

If you haven’t set the $LD_LIBRARY_PATH, you may raise an exception. There’s also an alternative to setting the $LD_LIBRARY_PATH before you call the gcc executable. You can use the -L option set the $LD_LIBRARY_PATH for a given all to the gcc executable, like:

gcc -L /home/student/Code/c/trylib/libfile -shared -fPIC -o bin/writestr.so src/writestr.c

Then, you compile the main.c program. You must put the writestr.so shared library before you designate the main target object and main.c source files, like this:

gcc bin/writestr.so -o bin/main src/main.c

Now, you can perform a C-only unit test case by calling the main executable. However, you must have set the $LD_LIBRARY_PATH environment variable at runtime too. You see the following reply to the “Enter file name and message” question when you run the main program unit:

bin/main
Enter file name and message: /home/student/Code/c/trylib/libfile/test.txt A long native string is the second input to this C program.

You can now see that the a new test.txt file has been written to the target directory, and that it contains the following string:

A long native string is the second input to this C program.

As always, I hope this helps those you want to write shared libraries in the C programming language.

Written by maclochlainn

May 7th, 2015 at 1:46 am

Visual Studio Freedom

without comments

Some of my students want to learn to write C++ on a Windows OS. At some point, you simply surrender to the fact that many people prefer the Windows OS as a starting point. Traditionally, I’d recommend the Microsoft Visual Studio as their learning vehicle because it’s free to our students because of our relationship with Microsoft. It’s not free to graduates. When a graduate contacts me I recommend Code::Blocks. Just recently, one ask for more than a recommendation. He wanted instructions. These are the instructions.

Download and Install Code::Blocks

Here are the instructions to install and download Code::Blocks 13.12.

CodeBlocks_01

  1. You can download Download and Install Code::Blocks from the web site. Then, you can install Code::Blocks from download folder.

CodeBlocks_02

  1. You launch the codeblocks-12.12mingw-setup.exe file from the download folder.

CodeBlocks_03

  1. This is the first screen of the Code::Blocks wizard. Click the Next button to continue.

CodeBlocks_04

  1. This is the license agreement. Click the I Agree button to continue.

CodeBlocks_05

  1. This screen shows the components to install. The default has all of them checked. I recommend you keep the default. Click the Next button to continue.

CodeBlocks_06

  1. This screen lets you accept the default install location or to chose another install location. I recommend you keep the default install location. Click the Install button to continue.

CodeBlocks_07

  1. This screen shows you the extracting and deployment of files. Click the Next button to continue.

CodeBlocks_08

  1. This indicates that you’ve installed the product, and it now prompts you to run Code::Blocks programscreen shows you the extracting and deployment of files. Click the Yes button to continue.

CodeBlocks_09

  1. This indicates that the installer detects a GNU GCC Compiler. Click the OK button to continue.

CodeBlocks_10

  1. This acknowledges the completion of the installation. Click the OK button to continue.

CodeBlocks_9a

  1. This dialog tells you the installation has completed. Click the Next button to continue.

CodeBlocks_9b

  1. This dialog completes the installation. Click the Finish button to end the installation.

Configure Code::Blocks

CodeBlocks_11

  1. This is the main menu of Code::Blocks application. You need to click the Create a new project link to continue.

CodeBlocks_12

  1. You should choose a Console application for this example. Double click the Console application icon to continue.

CodeBlocks_13

  1. This dialog launches the Console page. Check the Skip this page next time and then click the Next button to continue.

CodeBlocks_14

  1. This dialog lets you choose whether you want to write a C and C++ program. Click the Next button to continue.

CodeBlocks_15

  1. This dialog lets you choose whether you want to write a C and C++ program. Click the Next button to continue.

CodeBlocks_16

  1. This dialog lets you choose the compiler, debug, and release configurations. Click the Finish button to continue.

Create and run a program in Code::Blocks

CodeBlocks_17

  1. This dialog gives you an empty project. Click the Sources item in the list of the Project tab.

CodeBlocks_18

  1. This dialog adds a main.cpp to the list of the Management console. Click the main.cpp item in the list of the Project tab.

CodeBlocks_19

  1. After clicking the main.cpp item in the Project list, the Code::Blocks IDE generates the content of the main.cpp file. Click the Green Arrow to run (compile and execute) the main.cpp file. The endl is a defined in std, and like a \n line terminator.

CodeBlocks_20

  1. A new file hasn’t been compiled (or built), which means you get the following dialog. It wants to know if you want to build the program. Click the Yes button to build the program.

CodeBlocks_21

  1. After making the file, the Build Log tells you whether the code compiles or not. Click the Run green arrow to run the program.

CodeBlocks_22

  1. After running a Console application, you’ll see the output of your program in a console window like the following. You can close it by clicking the console window’s close button.

CodeBlocks_23

  1. After executing the compiled file, the Build Log tells you whether the program compiles successfully or not.

As always, I hope this helps those who read it. Good luck learning to write C/C++ programs.

Written by maclochlainn

July 5th, 2014 at 1:48 am

Posted in C/C++ Programming

Tagged with