Compiling the following code using gcc-5.1.0 produces a warning:
warning: implicit declaration of function ‘abs’ [-Wimplicit-function-declaration]
Code:
#include <stdio.h>
#include <math.h>
int main (void)
{
printf ("%d\n", abs (-1));
return 0;
}
I have compiled the same code with gcc-4.9.2 and it's not producing any warning.
The abs() function is declared in <stdlib.h> which you've not included.
GCC 4.9.2 didn't complain because the default compilation mode was C89/C90 (-std=gnu89) and functions did not need to be declared before being used in C89 as long as they returned an int, but the default compilation mode was changed to C11 (-stdd=gnu11) in GCC 5.1.0 (see the release notes) and in C11 functions must be declared (or defined) before they are used.
Try to include the <stdlib.h> in your code. The abs() function is defined inside the <stdlib.h>
Related
I have a simple program to test basename() method:
#include <stdio.h>
#include <string.h>
//#include <libgen.h>
int main (int argc , char **argv)
{
char *a = strdup("test();");
printf("%s", basename(a));
return 0;
}
clang complains but it compiles anyway.
test.c:7:18: warning: implicit declaration of function 'basename' is invalid in C99 [-Wimplicit-function-declaration]
printf("%p", basename(a));
^
test.c:7:18: warning: format specifies type 'void *' but the argument has type 'int' [-Wformat]
printf("%p", basename(a));
And it results in segfault. But if I added libgen.h header, it works normally.
I've checked the binary with otool, it linked against the same dylib, nothing else. Why does the first one crash?
I've checked the answer here already, it uses a static buffer but I use the result from strdup(), so it's a different question.
When trying to parse a number too big to fit a long, strtol() returns 0 instead of LONG_MAX (stdio.h). If I read the POSIX spec correctly, it should be LONG_MAX. There is a different between stdio.h and stdlib.h
#include "stdio.h"
int main(void){
printf("%ld\n", strtol("99999999999999999999999"));
return 0;
} # 0
#include "stdio.h"
//#include "stdlib.h"
int main(void){
char *end[500];
printf("%ld\n", strtol("99999999999999999999999", end, 10));
return 0;
} # 9223372036854775807
strtol is declared in header <stdlib.h> as
long strtol( const char *restrict str, char **restrict str_end, int base );
// ^^^^^^^^ ^^^^^^^^ since C99
In the first posted snippet, <stdlib.h> is not included and the function is called with one single argument, so that, if compiled with -Wall -Wextra -std=gnu11, gcc produces the following explanatory warnings before outputting 0:
prog.c: In function 'main':
prog.c:5:21: warning: implicit declaration of function 'strtol' [-Wimplicit-function-declaration]
printf("%ld\n", strtol("99999999999999999999999"));
^~~~~~
prog.c:5:15: warning: format '%ld' expects argument of type 'long int', but argument 2 has type 'int' [-Wformat=]
printf("%ld\n", strtol("99999999999999999999999"));
~~^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
%d
Which means that the library function is not called at all and an implicitly declared function with the same name is called, an int with value 0 is returned and printed (with the wrong format specifier, which is itself undefined behavior).
Note that the same code fails to compile with clang, which reports the following:
prog.c:4:21: warning: implicitly declaring library function 'strtol' with type 'long (const char *, char **, int)' [-Wimplicit-function-declaration]
printf("%ld\n", strtol("99999999999999999999999"));
^
prog.c:4:21: note: include the header <stdlib.h> or explicitly provide a declaration for 'strtol'
prog.c:4:53: error: too few arguments to function call, expected 3, have 1
printf("%ld\n", strtol("99999999999999999999999"));
~~~~~~ ^
1 warning and 1 error generated.
In the second snippet, strtol is called with the right number of arguments, but, as posted (with the #include commented out), has the same missing header problem. To produce the expected output, LONG_MAX, header stdlib.h has to be included.
I'm trying to use thrust::transform to operate on vectors of type thrust:complex<float> without success. The following example blows up during compilation with several pages of errors.
#include <cuda.h>
#include <cuda_runtime.h>
#include <cufft.h>
#include <thrust/device_vector.h>
#include <thrust/host_vector.h>
#include <thrust/transform.h>
#include <thrust/complex.h>
int main(int argc, char *argv[]) {
thrust::device_vector< thrust::complex<float> > d_vec1(4);
thrust::device_vector<float> d_vec2(4);
thrust::fill(d_vec1.begin(), d_vec1.end(), thrust::complex<float>(1,1));
thrust::transform(d_vec1.begin(), d_vec1.end(), d_vec2.begin(), thrust::abs< thrust::complex<float> >() );
}
I'm using CUDA 8.0 on Ubuntu Xenial and compiling with clang 3.8.0-2ubuntu4 using nvcc --std=c++11 main.cpp -o main.
Main errors appear to be:
main.cpp: In function ‘int main(int, char**)’:
main.cpp:17:105: error: no matching function for call to ‘abs()’
gin(), d_vec1.end(), d_vec2.begin(), thrust::abs< thrust::complex<float> >() );
and
/usr/local/cuda-8.0/bin/../targets/x86_64-linux/include/thrust/detail/complex/arithmetic.h:143:20: note: template argument deduction/substitution failed:
main.cpp:17:105: note: candidate expects 1 argument, 0 provided
gin(), d_vec1.end(), d_vec2.begin(), thrust::abs< thrust::complex<float> >() );
^
No problem working on real floats, but no such with complex ones. I'm thinking there's a type error that I'm missing, but I'm very much still on the steep part of the learning curve with Thrust & templates.
The error message is quite descriptive:
thrust::abs<thrust::complex<...>> is a function which expects exactly one parameter, see thrust/detail/complex/arithmetic.h#L143:
template <typename ValueType>
__host__ __device__
inline ValueType abs(const complex<ValueType>& z){
return hypot(z.real(),z.imag());
}
For your use case, you need to wrap that function by a functor:
struct complex_abs_functor
{
template <typename ValueType>
__host__ __device__
ValueType operator()(const thrust::complex<ValueType>& z)
{
return thrust::abs(z);
}
};
Finally, employ that functor here:
thrust::transform(d_vec1.begin(),
d_vec1.end(),
d_vec2.begin(),
complex_abs_functor());
I've found a strange problem during the compile of an example of ffmpeg in Qt Mac.
I have installed the ffmpeg library and I have tested the examples of this with cc and gcc compiler on the terminal, and I don't have any problem in the case of compile and run.
But when I call the library (ffmpeg are C library) in Qt for compile the same code of the example, the g++ compiler give me many error.
I have used this structure in the main.cpp code:
#include "mainwindow.h"
#include "ui_mainwindow.h"
#include <QFileDialog>
extern "C" {
#include <libavutil/imgutils.h>
#include <libavutil/samplefmt.h>
#include <libavutil/timestamp.h>
#include <libavformat/avformat.h>
}
#include <QDebug>
and the Compile Output gives me:
In file included from ../audvid/main.cpp:7:
/opt/local/include/libavutil/timestamp.h: In function 'char*
av_ts_make_string(char*, int64_t)':
/opt/local/include/libavutil/timestamp.h:48: warning: comparison
between signed and unsigned integer expressions
/opt/local/include/libavutil/timestamp.h:49: error: expected `)'
before 'PRId64' /opt/local/include/libavutil/timestamp.h:49: warning:
spurious trailing '%' in format
/opt/local/include/libavutil/timestamp.h:49: warning: too many
arguments for format /opt/local/include/libavutil/timestamp.h: At
global scope: /opt/local/include/libavutil/timestamp.h:68: error:
'AVRational' has not been declared
/opt/local/include/libavutil/timestamp.h: In function 'char*
av_ts_make_time_string(char*, int64_t, int*)':
/opt/local/include/libavutil/timestamp.h:70: warning: comparison
between signed and unsigned integer expressions
/opt/local/include/libavutil/timestamp.h:71: error: 'av_q2d' was not
declared in this scope ../audvid/main.cpp: In function 'int
decode_packet(int*, int)': ../audvid/main.cpp:50: error: cannot
convert 'AVRational*' to 'int*' for argument '3' to 'char*
av_ts_make_time_string(char*, int64_t, int*)' ../audvid/main.cpp:73:
error: cannot convert 'AVRational*' to 'int*' for argument '3' to
'char* av_ts_make_time_string(char*, int64_t, int*)'
../audvid/main.cpp:75: error: 'struct AVFrame' has no member named
'channels' ../audvid/main.cpp:84: error: 'struct AVFrame' has no
member named 'channels' ../audvid/main.cpp:90: error: 'struct AVFrame'
has no member named 'channels' ../audvid/main.cpp: In function 'int
open_codec_context(int*, AVFormatContext*, AVMediaType)':
../audvid/main.cpp:112: error: 'av_get_media_type_string' was not
declared in this scope ../audvid/main.cpp:123: error:
'av_get_media_type_string' was not declared in this scope
../audvid/main.cpp:129: error: 'av_get_media_type_string' was not
declared in this scope ../audvid/main.cpp: In function 'int
get_format_from_sample_fmt(const char**, AVSampleFormat)':
../audvid/main.cpp:152: warning: comparison between signed and
unsigned integer expressions ../audvid/main.cpp: In function 'int
main(int, char**)': ../audvid/main.cpp:239: error: invalid conversion
from 'void*' to 'uint8_t**' make: *** [main.o] Error 1 make: Leaving
directory
`/Users/polin/Desktop/audvid/audvid-build- Qt_4_8_0_qt_everywhere_opensource_src_4_8_0_tp-Release'
10:44:37: The process "/usr/bin/make" exited with code 2. Error while
building/deploying project audvid (target: Qt 4.8.0
(qt-everywhere-opensource-src-4.8.0-tp)) When executing step 'Make'
I don't understand if I make a mistake in the code or if I must change the Qt compiler? (and I don't know how can do this)
You need to include libavutil/avutil.h before #include <libavutil/imgutils.h>. Also you need to add #include <libavcodec/avcodec.h>
Because ffmpeg is written in pure C. Some C99 design is incompatible with g++ compiler. So one way to solve it is to find where the "wrong" source codes are and replace them with C++ design style.
e.g.
av_get_bytes_per_sample( static_cast<AVSampleFormat>(format) )
#undef av_err2str
#define av_err2str(errnum) \
av_make_error_string((char*)__builtin_alloca(AV_ERROR_MAX_STRING_SIZE), AV_ERROR_MAX_STRING_SIZE, errnum)
#undef av_ts2timestr
#define av_ts2timestr(ts, tb) \
av_ts_make_time_string((char*)__builtin_alloca(AV_TS_MAX_STRING_SIZE), ts, tb)
I am having issues with usage of log10f().
I am compiling the program on Linux (2.6.28-11-generic) and using gcc (3.4.6).
The following source compiles and prints 1.000000 on execution.
#include <stdio.h>
#include <math.h>
int main() {
printf("%f\n", log10f(10));
return 0;
}
while the below one doesn't and throws up link error:
#include <stdio.h>
#include <math.h>
int main() {
printf("%f\n", log10f(100));
return 0;
}
Error : Undefined reference to log10f
Is the log10f() not defined as part of standard math library (Man pages indicate that it is part of math library)?
Why is that the second example doesn't compile?
That's because the required libm.a library is not linked into the executable automatically.
You have to add the -lm parameter to gcc. Then the linker will also link libm.a into your executable.