Another, different open() returns 0 - gcc

In searching the site, I found two other similar (at first glance) questions by users 2253605
and 2135159. I also have tried two different versions of gcc. This started out as a hard to
track problem in an application to keep various forms of data in sync on different media. I
eventually boiled it down to a few lines of code that illustrate the problem.
This one is very defined and puzzling. I have not been able to find a case where my system opens
a file, and returns a non-zero file descriptor. It sometimes does really open the specified file
and allows a subsequent read() to occur without error. But by the third open() the
subsequent read() fails, specifying an invalid argument, which can only be a zero value file
descriptor.
The code below tries to open 5 different files, 4 files exist and one that does not exist.
The first 4 opens all return a file descriptor value of zero (stdin).
stdin is not closed, a read() before the first open() or after any one of these open() calls,
will hang until enter is pressed.
Even if stdin were closed, zero should only be returned for the first open(). The
file descriptors are being set and when the open() for the non-existent file is attempted,
it returns an error.
I can't believe that gcc can't open a file. I think I have some kind of O/S-compiler configuration
issue (lib) or maybe I can't see the forest for the trees.
This is on ubuntu 12.04 LTS 64 bit and 64 bit gcc-4.6 also on gcc-4.7 . The flash drive is
formatted ext4. x86_64 intel processor. The installation commands used for gccc-4.7 on 2/10/16
are also shown below. Both gcc-4.6 and gcc-4.7 give identical results. The makefile
is at the end.
Anybody know what's happening here?
The terminal output is shown below the code.
#include <stdio.h>
#include <fcntl.h>
#include <unistd.h
#include <errno.h>
int main()
{
long ret_val;
char cpy_buf[4096];
char s_ary[20][80] =
{
"/media/FLASH16GB_2/Test_dir/t_dir/dm1", //0 exists
"/media/FLASH16GB_2/Test_dir/t_dir/dm2", //1 exists
"/media/FLASH16GB_2/Test_dir/t_dir/dm3", //2 exists
"/media/FLASH16GB_2/Test_dir/t_dir/dm4", //3 exists
"/media/FLASH16GB_2/Test_dir/t_dir/dm5", //4 does not exist
};
char *s1;
long s_fh_1, s_fh_2, s_fh_3, s_fh_4, s_fh_5;
s_fh_1 = 10000;
s1 = &s_ary[0][0];
if (s_fh_1 = open( s1 , O_RDONLY) < 0) // &s_ary[0][0]
{
printf("Error opening source file, name=%s, line# = %i, errno = %i \n",&s_ary[0][0], __LINE__ , errno);
return -1;
}
if (s_fh_2 = open( &s_ary[1][0], O_RDONLY) < 0)
{
printf("Error opening source file, name=%s, line# = %i, errno = %i \n",&s_ary[1][0], __LINE__ , errno);
return -1;
}
if (s_fh_3 = open( &s_ary[2][0], O_RDONLY,0) < 0)
{
printf("Error opening source file, name=%s, line# = %i, errno = %i \n",&s_ary[2][0], __LINE__ , errno);
return -1;
}
if (s_fh_4 = open( &s_ary[3][0], O_RDONLY,0) < 0)
{
printf("Error opening source file, name=%s, line# = %i, errno = %i \n",&s_ary[3][0], __LINE__ , errno);
return -1;
}
printf("s_fh_1 = %li, s_fh_2 = %li, s_fh_3 = %li, s_fh_4 = %li \n", s_fh_1, s_fh_2, s_fh_3, s_fh_4);
if (s_fh_5 = open( &s_ary[4][0], O_RDONLY,0) < 0)
{
printf("Error opening source file, name=%s, line# = %i, errno = %i \n",&s_ary[4][0], __LINE__ , errno);
return -1;
}
return 0;
}
terminal output:
$ make
gcc -g -c -std=iso9899:1999 -o obj/bug_tst_sync_m.o bug_tst_sync_m.c -I../include
gcc -o bug_tst_sync_m obj/bug_tst_sync_m.o -I../include -L /usr/lib64/X11 -lX11 -lm
$ ./bug_tst_sync_m
s_fh_1 = 0, s_fh_2 = 0, s_fh_3 = 0, s_fh_4 = 0
Error opening source file, name=/media/FLASH16GB_2/Test_dir/t_dir/dm5, line# = 88, errno = 2
$
$
gcc-4.7 installation commands used on 2_10_16.
update-alternatives --display gcc
sudo add-apt-repository ppa:ubuntu-toolchain-r/test
sudo apt-get update
sudo apt-get install gcc-4.7
sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-4.7 60
sudo update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-4.6 40
sudo update-alternatives --config gcc
makefile
### where to look for include files ( locally and globally ? -I /usr/include/X11)
IDIR =../include
### compiler to runand generate debugging info (no -g for production release code)
CC=gcc -g
### list of dependencies
CFLAGS=-I$(IDIR)
### where to put object modules
ODIR=obj
### where to look for local library files locally (or write?)
LDIR = -L /usr/lib64/X11 -lX11
### libraries to include m=-lm includes the math libarary, math lib = -lm
LIBS=-lm
### list of all dependency files (.h files)
_DEPS = queues.h InterlockedExchange.h
DEPS = $(patsubst %,$(IDIR)/%,$(_DEPS))
### list of all object files
_OBJ = bug_tst_sync_m.o
OBJ = $(patsubst %,$(ODIR)/%,$(_OBJ))
### compiles object modules and produces debug info
$(ODIR)/%.o: %.c $(DEPS)
$(CC) -c -std=iso9899:1999 -o $# $< $(CFLAGS)
### left side of colon is executable name
### this line links objects and creates the executable
bug_tst_sync_m: $(OBJ)
gcc -o $# $^ $(CFLAGS) $(LDIR) $(LIBS)
### this gets run if you type "make clean". it deletes source backup and object files.
### run this then next make does everything. Without this you get situations that
.PHONY: clean
clean:
rm -f $(ODIR)/*.o *~ core $(INCDIR)/*~

Your problem is operator precedence, < binds harder than =;
if ( s_fh_1 = open(s1 , O_RDONLY) < 0 )
becomes
if ( s_fh_1 = ( open(s1 , O_RDONLY) < 0 ) )
which means, if open returns a number greater than or equal to zero, s_fh_1 will be 0.

Related

How do I install primer3 on windows?

Problem:
I need to install Primer3, a widely used bio tool that finds allows one to design primers.
Attempts at resolution:
I have attempted to follow their instructions for a Windows installation to no avail as it does not seem provide enough information. I not a experienced programmer by any means. So far I've also referenced this stack overflow post about a similar issue and tried to follow the suggested answer. I also briefly looked at a thread in their github repository, though I can't really understand what they are saying in it. Nothing seems to work so far as the output I get from my command terminal (the mingw32 version) is this:
C:\Users\mqian\Desktop\CGIProject\primer3-2.4.0\primer3-2.4.0\test>mingw32-make
TESTOPTS=--windows
cd ..\src & mingw32-make
mingw32-make[1]: Entering directory 'C:/Users/mqian/Desktop/CGIProject/primer3-2
.4.0/primer3-2.4.0/src'
g++ -c -g -Wall -D__USE_FIXED_PROTOTYPES__ -O2 masker.c
masker.c:8:22: fatal error: sys/mman.h: No such file or directory
compilation terminated.
Makefile:226: recipe for target 'masker.o' failed
mingw32-make[1]: *** [masker.o] Error 1
mingw32-make[1]: Leaving directory 'C:/Users/mqian/Desktop/CGIProject/primer3-2.
4.0/primer3-2.4.0/src'
Makefile:94: recipe for target 'makeexes' failed
mingw32-make: *** [makeexes] Error 2
and if I just try to run a make in the src folder:
C:\Users\mqian\Desktop\CGIProject\primer3-2.4.0\primer3-2.4.0\src>mingw32-make
g++ -c -g -Wall -D__USE_FIXED_PROTOTYPES__ -O2 masker.c
masker.c:8:22: fatal error: sys/mman.h: No such file or directory
compilation terminated.
Makefile:226: recipe for target 'masker.o' failed
mingw32-make: *** [masker.o] Error 1
Is it something that I missing in terms of a software or package needed? Is their makefile bugged? Any help would be appreciated.
P.S. here is a link to their download site on sourceforge. I am using version 2.4.0.
I was able to build it like this on Windows (replace /usr/local with the path where you want to install):
Build mman-win32 from https://github.com/witwall/mman-win32/releases under MSYS2 using:
./configure --prefix=/usr/local --cc=gcc --enable-static --enable-shared &&
make &&
mkdir -p /usr/local/include/mman-win32/sys /usr/local/lib &&
cp -f *.h /usr/local/include/mman-win32/sys/ &&
cp -f *.a /usr/local/lib/ &&
echo Success
Then build primer3 from https://github.com/primer3-org/primer3/releases:
mv src/masker.c src/masker.c.bak
cat > src/masker.c << EOF
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define GETLINE_BUFLEN 128
static ssize_t getline(char** lineptr, size_t* n, FILE* stream)
{
char* bufptr;
char* p;
ssize_t size;
int c;
if (!lineptr || !n || !stream)
return -1;
bufptr = *lineptr;
size = *n;
c = fgetc(stream);
if (c == EOF)
return -1;
if (!bufptr) {
if ((bufptr = (char*)malloc(GETLINE_BUFLEN)) == NULL)
return -1;
size = GETLINE_BUFLEN;
}
p = bufptr;
while (c != EOF) {
if ((p - bufptr) > (size - 1)) {
size = size + GETLINE_BUFLEN;
if ((bufptr = (char*)realloc(bufptr, size)) == NULL)
return -1;
}
*p++ = c;
if (c == '\n') {
break;
}
c = fgetc(stream);
}
*p++ = 0;
*lineptr = bufptr;
*n = size;
return p - bufptr - 1;
}
EOF
cat src/masker.c.bak >> src/masker.c
make -Csrc install PREFIX=/usr/local CC_OPTS="-I/usr/local/include/mman-win32" LDLIBS="-Wl,--as-needed -lmman" &&
echo Success

XCode IDE Library settings versus gcc make files

I have spent a lot of time researching how to compile a simple PostgreSQL test application written in C and I've got it to compile, run and connect to the PostgreSQL database that comes with Mavericks Server om my Mac Mini running OS X 10.9.3.
Then I decided to try using the Xcode IDE to compile and debug the same PostgreSQL code however, in Xcode I am getting references to Postgres methods listing 7 issues related to "Apple Mach-O Linker (ld) Error", including _PQclear, _PQconnectdb, PQerrorMessage, _PQexec, _PQfinish, _PQprint, _PQstatus. The final error is related to Linker command failed with exit code 1 (use -v to see invocation). Note: I'm not sure where to add the -ld parameters in the Xcode IDE or where to put the -v to find out more.
I have read many of the Stack Overflow items but most of them relate to iOS rather than OSX however I tried to figure out how to use many of those suggestions. Unfortunately I still am not able to figure out where to add the ld (LD) item for postgres similar to what I have in my make file. I tried adding and changing different settings on the Build Phases in the Xcode IDE but I keep getting these 8 issues.
In my code that I'm trying to compile from Xcode I changed one line to point to the location where the libpq-fe.h is as follows but I'm not sure if this is the correct or best approach:
#include </Applications/Server.app/Contents/ServerRoot/usr/include/libpq-fe.h>
Here is my makefile that compiles using make pg_test
## File: makefile
## Rules to create libpq sample application
LDLIBS += -L/Applications/Server.app/Contents/ServerRoot/usr/lib/postgresql9.1/ -lpq
CFLAGS += -c -v -g -I/Applications/Server.app/Contents/ServerRoot/usr/include/
LDFLAGS += -g
pg_test: pg_test.o
Here is my pg_test.c code
// File: pg_test.c
#include <stdlib.h>
#include <libpq-fe.h>
void process_query (PGconn * connection, const char * query_text ) {
PGresult * result;
PQprintOpt options = {0};
if(( result = PQexec ( connection, query_text )) == NULL ) {
printf( "%s\n", PQerrorMessage ( connection ));
return;
}
options.header = 1;
options.align = 1;
options.fieldSep = "|";
PQprint (stdout, result, &options );
PQclear ( result );
}
int main ( ) {
PGconn * connection;
char * dbarg = "user=jerry password=test dbname=jletter hostaddr=127.0.0.1 port=5432";
connection = PQconnectdb(dbarg);
if( PQstatus( connection ) != CONNECTION_OK )
printf( "%s\n", PQerrorMessage( connection ));
else {
process_query( connection, "SELECT * FROM friends" );
}
PQfinish ( connection );
exit (0);
}
Any help would be greatly appreciated.

Display kernel error

I'm using GCC and the NVIDIA implementation of OpenCL, and online compilation instead of offline compilation.
I use this list to check which is the error I have. But nevertheless if I have an error inside my kernel the only information I have is an error value -48.
My question is: Is there a way to display the exact kernel compilation error?
If a semicolon is missing, or I have a wild pointer I would like to read so, instead of just a -48 error. Otherwise the development time is getting too slow.
I add also my Makefile:
CC=gcc
FILE=main
all:
$(CC) -c -Wall -I /usr/local/cuda/include/ $(FILE).c -o $(FILE).o
$(CC) $(FILE).o -o $(FILE) -L /usr/local/cuda/lib64/ -l OpenCL
clean:
$(RM) $(FILE) $(FILE).o
In C++, do something like:
int ErrorCode = 0;
cl_program P;
cl_device_id D;
size_t LogSize;
cl_build_status BuildStatus;
//Configure OpenCL
//Load Program Here
//Compile Program here
//Check the status of compilation
ErrorCode = clGetProgramBuildInfo(P, D, CL_PROGRAM_BUILD_STATUS, NULL, NULL, &BuildStatus);
if(BuildStatus == CL_BUILD_ERROR){
//Fetch Error
ErrorCode = clGetProgramBuildInfo(P, D, CL_PROGRAM_BUILD_LOG, NULL, NULL, &LogSize);
char Log = new Log[LogSize]; //Or use Malloc if in C
ErrorCode = clGetProgramBuildInfo(P, D, CL_PROGRAM_BUILD_LOG, LogSize, Log, NULL);
//Display Error Code here, close out OpenCL, try again, etc
}

libtool doesn't provide library dependencies to link

I am using libtool 2.2.6b on ubuntu lucid, and libtool 2.4.2 on ubuntu precise. On lucid my project will link properly. On precise it fails to link. Here's example code that demonstrates my problem;
configure.ac
AC_INIT([ltp], [0.0.1], [someone])
AM_INIT_AUTOMAKE
AC_CONFIG_HEADERS([config.h])
AC_CONFIG_MACRO_DIR([.m4])
AC_CONFIG_FILES([Makefile foo/Makefile bar/Makefile wah/Makefile])
AC_PROG_CXX
AC_PROG_LIBTOOL
AM_SANITY_CHECK
AC_LANG_CPLUSPLUS
AC_OUTPUT
Makefile.am
SUBDIRS = foo bar wah
ACLOCAL_AMFLAGS = -I .m4
foo/Foo.h
#ifndef FOO_FOO_H_
#define FOO_FOO_H_
namespace Foo
{
class Foo
{
public:
Foo(long l);
private:
long l;
};
}
#endif
foo/Foo.cpp
#include "foo/Foo.h"
namespace Foo
{
Foo::Foo(long l) : l(l) {}
}
foo/Makefile.am
lib_LTLIBRARIES = libfoo.la
libfoo_la_SOURCES = Foo.cpp
libfoo_la_CPPFLAGS =
libfoo_la_LDFLAGS = -release 0.0.1
libfoo_la_LIBADD =
bar/Bar.h
#ifndef BAR_BAR_H_
#define BAR_BAR_H_
#include "foo/Foo.h"
namespace Bar
{
class Bar
{
public:
Bar(const Foo::Foo & f);
private:
Foo::Foo f;
};
}
#endif
bar/Bar.cpp
#include "bar/Bar.h"
namespace Bar
{
Bar::Bar(const Foo::Foo & f) : f(f) { }
}
bar/Makefile.am
lib_LTLIBRARIES = libbar.la
libbar_la_SOURCES = Bar.cpp
libbar_la_CPPFLAGS =
libbar_la_LDFLAGS = -release 0.0.1
libbar_la_LIBADD = -L../foo -lfoo
wah/main.cpp
#include "bar/Bar.h"
int main(int argc, char * argv[])
{
Bar::Bar( 5 );
return 0;
}
wah/Makefile.am
bin_PROGRAMS = wah
wah_SOURCES = main.cpp
wah_CPPFLAGS =
wah_LDADD = -L../bar -lbar
On Lucid, wah links, on Precise, it fails with:
wah/main.cpp:5 undefined reference to `Foo::Foo::Foo(long)'
I can fix this by adding -L../foo -lfoo to wah_LDADD, but really, isn't libtool supposed to do that for me automagically? The libtool manual section on `Linking executables' seems to indicate that is exactly what it should do.
On any Debian machine I use for development, I have to compile and install Libtool by hand, because the Debian-supplied version is patched and ignores dependencies in a way that break my builds.
If Ubuntu's version is similar, you might want to install Libtool from source too.
I suppose you could say it's more of a difference in philosophy. The point of Debian's change is to encourage users to be explicit about what they depend on, which reduces the amount of unnecessary churn when dependencies deep down the tree get upgraded.
When link_all_deplibs=yes (unmodified libtool), if your program wah depends on bar and bar depends on foo, then it is implied that wah depends foo as well.
When link_all_deplibs=no (Debian's modified libtool), if your program wah depends on bar and bar depends on foo, then it is not implied that wah depends foo as well.
So, taking Debian's perspective, this is false in your program: wah does depend on foo by virtue of this line:
Bar::Bar( 5 );
Here, you are calling the constructor of Foo::Foo implicitly. As far as the C++ compiler is concerned, your program is really more like:
Bar::Bar( Foo::Foo( 5 ) );
Therefore, wah depends on foo not just indirectly, but directly. Hence, from Debian's perspective, you are should explicitly link to foo via -lfoo.
In particular, this is not the same situation as libtool's example for Linking Executables. In that example, main.o does not explicitly depend on libm, thus -lm should, in principle, be unnecessary when linking the main.o (main.c does not call cos directly). Perhaps the reason why libtool links recursively is as a work around for older systems where linkers are unable to handle indirect dependencies?
Works for me on Ubuntu 12.04 (Precise Pangolin) 32-bit, libtool 2.4.2.
I did have to change your Makefiles a bit to make dist (more) correctly:
foo/Makefile.am:
lib_LTLIBRARIES = libfoo.la
libfoo_la_SOURCES = Foo.cpp Foo.h
libfoo_la_CPPFLAGS =
libfoo_la_LDFLAGS = -release 0.0.1
libfoo_la_LIBADD =
bar/Makefile.am:
lib_LTLIBRARIES = libbar.la
libbar_la_SOURCES = Bar.cpp Bar.h
libbar_la_CPPFLAGS =
libbar_la_LDFLAGS = -release 0.0.1
libbar_la_LIBADD = -L../foo -lfoo
wah/Makefile.am
bin_PROGRAMS = wah
wah_SOURCES = main.cpp ../bar/Bar.h
wah_CPPFLAGS =
wah_LDADD = -L../bar -lbar
Here's how it links main.cpp:
make[2]: Entering directory `/xxx/ltp-0.0.1/wah'
g++ -DHAVE_CONFIG_H -I. -I.. -g -O2 -MT wah-main.o -MD -MP -MF .deps/wah-main.Tpo -c -o wah-main.o `test -f 'main.cpp' || echo './'`main.cpp
mv -f .deps/wah-main.Tpo .deps/wah-main.Po
/bin/bash ../libtool --tag=CXX --mode=link g++ -g -O2 -o wah wah-main.o -L../bar -lbar
libtool: link: g++ -g -O2 -o .libs/wah wah-main.o -L../bar /xxx/ltp-0.0.1/bar/.libs/libbar.so -L../foo /xxx/ltp-0.0.1/foo/.libs/libfoo.so
isn't libtool supposed to do that for me automagically?
Yes, it does, at least when the distribution tarball is created on a non-Ubuntu distribution. After I autoreconf on an Ubuntu box, I get the same error you do.
Apparently (according to adl) the Ubuntu distro has a patched version of libtool which sets the libtool script variable:
link_all_deplibs=no
I patched the configure generated libtool script to replace all these instances with:
link_all_deplibs=unknown
and everything linked as expected. I suppose you could do the same in a script that invokes autoreconf. Or install a non-patched version of libtool on the Ubuntu host. Or patch the patched libtool on the Ubuntu host. So there's a few options on how to fix it.

Compile a binary file for linking OSX

I'm trying to compile a binary file into a MACH_O object file so that it can be linked it into a dylib. The dylib is written in c/c++.
On linux the following command is used:
ld -r -b binary -o foo.o foo.bin
I have tried various option on OSX but to no avail:
ld -r foo.bin -o foo.o
gives:
ld: warning: -arch not specified
ld: warning: ignoring file foo.bin, file was built for unsupported file format which is not the architecture being linked (x86_64)
An empty .o file is created
ld -arch x86_64 -r foo.bin -o foo.o
ld: warning: ignoring file foo.bin, file was built for unsupported file format which is not the architecture being linked (x86_64)
Again and empty .o file is created. Checking the files with nm gives:
nm foo.o
nm: no name list
The binary file is actually, firmware that will be downloaded to an external device.
Thanks for looking
Here's the closest translation to the Linux linker command to perform binary embedding with the OSX linker:
touch stub.c
gcc -o stub.o -c stub.c
ld -r -o foo.o -sectcreate binary foo_bin foo.bin stub.o
foo.bin will be stored in segment binary, section foo_bin (both names are arbitrary but chosen to mimic GNU ld for ELF on Linux) of the foo.o object.
stub is necessary because ld refuses to create just a custom segment/section. You don't need it if you link directly with a real code object.
To get data back from the section, use getsectbyname (struct is defined in mach-o/loader.h):
#include <mach-o/getsect.h>
const struct section_64 *sect = getsectbyname("binary", "foo_bin");
char *buffer = calloc(1, sect->size+1);
memcpy(buffer, sect->addr, sect->size); // whatever
or getsectdata:
#include <mach-o/getsect.h>
size_t size;
char *data = getsectdata("binary", "foo_bin", &size);
char *buffer = calloc(1, size+1);
memcpy(buffer, data, size); // whatever
(I used it to store text data, hence the stringification via calloc zeroing of size+1 plus blob copying)
Warning: Since 10.7, ASLR got stronger and messes badly with getsect* functions, resulting in segfaults. set disable-aslr off in GDB before running to reproduce EXC_BAD_ACCESS (SIGSEGV) in debug conditions. People had to jump through inordinate hoops to find the real address and get this working again.
A simple workaround is to get the offset and size, open the binary and read the data straight from disk. Here is a working example:
// main.c, build with gcc -o main main.c foo.o
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>
#include <string.h>
#include <stdio.h>
#include <mach-o/getsect.h>
int main() {
// finding the filename of the running binary is left as an exercise to the reader
char *filename = "main";
const struct section_64 *sect = getsectbyname("binary", "foo_bin");
if (sect == NULL) {
exit(1);
}
char *buffer = calloc(1, sect->size+1);
int fd = open(filename, O_RDONLY);
if (fd < 0) {
exit(1);
}
lseek(fd, sect->offset, SEEK_SET);
if (read(fd, buffer, sect->size) != sect->size) {
close(fd);
exit(1);
}
printf("%s", buffer);
}

Resources