2017-03-14 6 views
-1

Afin de déterminer la durée de la vidéo pour un fichier donné, j'utilise libavformat. Mon programme se présente comme suit:gcc compile le code libavformat, mais g ++ ne le fait pas

#include <stdio.h> 
#include <libavformat/avformat.h> 
#include <libavutil/dict.h> 
int main (int argc, char **argv) { 
    AVFormatContext *fmt_ctx = NULL; 
    int ret; 
    if (argc != 2) { 
     printf("usage: %s <input_file>\n", argv[0]); 
     return 1; 
    } 
    av_register_all(); 
    if ((ret = avformat_open_input(&fmt_ctx, argv[1], NULL, NULL))) 
     return ret; 
    int64_t duration = fmt_ctx->duration; 
    int hours, mins, secs; 
    secs = duration/AV_TIME_BASE; 
    mins = secs/60; 
    secs %= 60; 
    hours = mins/60; 
    mins %= 60; 
    printf("Duration: %02d:%02d:%02d\n", hours, mins, secs); 
    avformat_free_context(fmt_ctx); 
    return 0; 
} 

Mon problème est que si gcc compile le code très bien, g ++ donc sans se plaindre aussi bien, mais le fichier objet créé ne peut ni être lié par gcc, ni g ++. Ou pour être plus précis:

gcc -c duration.c 
gcc -o duration duration.o -lavformat 
./duration my_movie.mp4 

fonctionne. Mais cela

g++ -c duration.C# "works" as in "g++ does not complain" 
g++ -o duration duration.o -lavformat # (gcc produces the same output after compiling with g++) 
duration.o: In function `main': 
duration.c:(.text+0x41): undefined reference to `av_register_all()' 
duration.c:(.text+0x62): undefined reference to `avformat_open_input(AVFormatContext**, char const*, AVInputFormat*, AVDictionary**)' 
duration.c:(.text+0x18c): undefined reference to `avformat_free_context(AVFormatContext*)' 
collect2: error: ld returned 1 exit status 

ne fonctionne pas. Cela m'amène à la conclusion que g ++ ne produit pas de code qui peut être lié correctement (dans ce cas). Je voudrais vraiment que cela fonctionne avec g ++ car cela fait partie d'un plus grand projet C++ et ce serait un peu le bazar de toujours devoir compiler des fichiers qui utilisent cette bibliothèque avec gcc à la place. Est-ce que quelqu'un sait pourquoi g ++ ne compilera pas ce programme correctement?

+1

Peut-être un nom numéro mutiler? Essayez d'envelopper les includes avec 'extern" C "' – Dmitri

+1

On dirait que vous avez un problème avec le nom-mangling. Vous pourriez essayer d'arroser 'extern 'C" 'autour. Ou, acceptez que C et C++ sont des langages distincts. – EOF

+0

Pourquoi pensez-vous que le code c devrait être compilé en tant que langue différente? – Olaf

Répondre

1

Cette erreur nous dit tout ce que nous devons savoir:

duration.c:(.text+0x62): undefined reference to `avformat_open_input(AVFormatContext**, char const*, AVInputFormat*, AVDictionary**)' 

L'éditeur de liens ne connaîtrait pas le type des arguments à moins qu'il pensait qu'il était une fonction C++. Donc, vous devez faire ceci:

extern "C" { 
#include <libavformat/avformat.h> 
#include <libavutil/dict.h> 
} 

Normalement, les fichiers d'en-tête auraient la partie extern "C" en eux. Le projet FFmpeg ne semble pas intéressé à le faire. Certains des en-têtes peuvent inclure des constructions C qui ne sont pas compatibles avec C++, comme indiqué dans FFmpeg ticket #3626.

Si vous rencontrez ces problèmes, vous devez écrire une cale en C.

+0

Oh mon garçon, c'était simple! Je n'ai pas vu ce langage construire avant, mais ça a marché, merci! – ryan91