Unité D'essai C Code [fermé]

j'ai travaillé sur un système intégré cet été écrit en ligne droite C. C'était un projet existant que l'entreprise pour laquelle je travaille avait repris. Je me suis habitué à écrire des tests unitaires en Java en utilisant JUnit, mais je n'ai pas trouvé la meilleure façon d'écrire des tests unitaires pour le code existant (qui nécessite un remaniement) ainsi que pour le nouveau code ajouté au système.

y a-t-il un moyen de rendre les tests unitaires de code C simple aussi faciles que les tests unitaires de code Java avec, pour exemple, JUnit ? Toute idée qui s'appliquerait spécifiquement au développement intégré (compilation croisée avec la plate-forme arm-linux) serait grandement appréciée.

730
demandé sur Paul Osborne 2008-09-15 23:12:00

30 réponses

un cadre d'essai unitaire en C est vérifier ; une liste des cadres d'essai unitaires en C se trouve ici et est reproduite ci-dessous. Selon le nombre de fonctions standard de votre bibliothèque, vous pouvez ou non utiliser l'une d'entre elles.

AceUnit

AceUnit (Advanced C and Embedded Unit) se présente comme un cadre de test confortable pour les unités de code C. Il essaie de mimick JUnit 4.x et comprend des capacités de réflexion. AceUnit peut être utilisé dans des environnements de contraintes de ressources, par exemple le développement de logiciels embarqués, et il fonctionne très bien dans des environnements où vous ne pouvez pas inclure un seul fichier d'en-tête standard et ne pouvez pas invoquer une seule fonction C standard à partir des bibliothèques ANSI / ISO C. Il dispose également d'un port Windows. Elle n'utilise pas de fourches pour piéger les signaux, bien que les auteurs aient exprimé leur intérêt à ajouter une telle caractéristique. Voir le AceUnit page d'accueil .

GNU Autounit

un peu dans le même sens que Check, y compris bifurquer pour exécuter des tests unitaires dans un espace d'adresse séparé (en fait, L'auteur original de Check a emprunté L'idée à GNU Autounit). GNU Autounit utilise glib de manière extensive, ce qui veut dire que la liaison et d'autres ont besoin d'options spéciales, mais ce n'est peut-être pas un gros problème pour vous, surtout si vous utilisez déjà GTK ou GLib. Voir le GNU Autounit page d'accueil .

cUnit

utilise également GLib, mais ne fourche pas pour protéger l'adresse de l'unité d'essais.

CUnit

Standard C, avec des plans pour une implémentation de L'interface graphique Win32. Ne protège pas actuellement l'espace d'adresse des tests unitaires. Au tout début du développement. Voir le CUnit page d'accueil .

CuTest

Un simple cadre avec un seul .c et l'un .h fichier que vous déposez dans votre arborescence des sources. Voir le Mignon page d'accueil .

CppUnit

le premier unit testing framework pour C++; vous pouvez également l'utiliser pour tester le code C. Il est stable, activement développé, et dispose d'une interface graphique. Les principales raisons de ne pas utiliser CppUnit pour C sont d'abord qu'il est assez grand, et ensuite vous devez écrire vos tests en C++, ce qui signifie que vous avez besoin d'un compilateur C++. Si ceux-ci ne semblent pas être des préoccupations, il est certainement intéressant de considérer, avec d'autres cadres de test des unités C++. Voir le CppUnit page d'accueil .

embUnit

embUnit (Embedded Unit) est un autre cadre d'essai unitaire pour les systèmes embarqués. Celui-ci semble être remplacé par AceUnit. "1519440920 Intégrés à l'Unité de la page d'accueil .

MinUnit

Un ensemble minimal de macros et c'est tout! Le but est de montrer à quel point il est facile de tester votre code. Voir le MinUnit homepage .

CUnit pour M. Ando

Un CUnit mise en œuvre qui est assez nouveau, et, apparemment, encore au début de leur développement. Voir le CUnit pour M. Ando homepage .

dernière mise à jour de cette liste: mars 2008.

autres:

CMocka

CMocka est un cadre de test pour C avec support pour objets simulés. Il est facile à utiliser et à installer. CMocka page d'accueil officielle.

critère

Le critère

est un cadre d'essais d'unités c multiplateformes supportant l'enregistrement automatique des essais, les essais paramétrés, les théories, et qui peut être produit sur des formats multiples, y compris TAP et JUnit XML. Chaque test est exécuté selon son propre processus, de sorte que les signaux et les accidents peuvent être signalés ou testés si nécessaire. Voir le "1519730920 Critère" page d'accueil pour plus d'informations.

HWUT

HWUT est un outil de Test D'unité générale avec un grand soutien pour C. Il peut aider à créer des Makefiles, générer des cas de test massifs codés dans des 'tables d'itération' minimales, marcher le long des machines d'état, générer des c-stubs et plus. L'approche générale est assez unique: les Verdicts sont basés sur le "bon stdout/mauvais stdout'. La fonction de comparaison, cependant, est flexible. Ainsi, n'importe quel type de script peut être utilisé pour le contrôle. Il peut être appliqué à n'importe quelle langue qui peut produire une sortie standard. Voir HWUT homepage.

Wikipedia donne une liste détaillée des cadres de test des unités C sous liste des cadres de test des unités: C

421
répondu Cody Piersall 2018-06-13 19:47:57

personnellement j'aime le Google test framework .

la vraie difficulté dans le test du code C est de briser les dépendances sur les modules externes pour pouvoir isoler le code dans les unités. Cela peut être particulièrement problématique lorsque vous essayez d'obtenir des tests autour de l'héritage de code. Dans ce cas, je me retrouve souvent à utiliser le linker pour utiliser les fonctions stubs dans les tests.

C'est ce à quoi les gens font référence quand ils parlent " coutures ". Dans C votre seule option est vraiment d'utiliser le pré-processeur ou le linker pour simuler vos dépendances.

une suite de test typique dans un de mes projets C pourrait ressembler à ceci:

#include "myimplementationfile.c"
#include <gtest/gtest.h>

// Mock out external dependency on mylogger.o
void Logger_log(...){}

TEST(FactorialTest, Zero) {
    EXPECT_EQ(1, Factorial(0));
}

notez que vous incluez en fait le fichier C et non le fichier d'en-tête . Cela donne l'avantage d'avoir accès à toutes les données membres statiques. Ici, je se moquer de mon enregistreur (qui peut être enregistreur.o et donnez une implémentation vide. Cela signifie que le fichier de test compile et se lie indépendamment du reste de la base de code et s'exécute de manière isolée.

quant à la compilation croisée du code, pour que cela fonctionne, vous avez besoin de bonnes installations sur la cible. J'ai fait cela avec googletest cross compilé Pour Linux sur une architecture PowerPC. Cela a du sens parce que là vous avez une coquille complète et os pour recueillir vos résultats. Pour les environnements moins riches (que je classe comme n'importe quoi sans OS complet), vous devriez simplement construire et exécuter sur l'hôte. Vous devriez le faire de toute façon pour que vous puissiez exécuter les tests automatiquement dans le cadre de la construction.

je trouve que tester le code C++ est généralement beaucoup plus facile en raison du fait que le code OO est en général beaucoup moins couplé que procédural (bien sûr cela dépend beaucoup du style de codage). Aussi dans C++ vous pouvez utiliser des trucs comme l'injection de dépendance et la méthode de dépassement pour obtenir des coutures dans le code qui est autrement encapsulé.

Michael Plumes a un excellent livre sur les tests de code legacy . Dans un chapitre, il traite des techniques pour traiter le code non-OO que je recommande fortement.

Edit : j'ai écrit un post de blog à propos de unit testing procedural code, avec source disponible sur GitHub .

Edit : il y a un nouveau Livre venant des programmeurs pragmatiques qui traite spécifiquement Unité de test C code qui je recommande fortement .

141
répondu mikelong 2011-04-11 09:40:02

Minunit est un cadre de test unitaire incroyablement simple. Je l'utilise pour tester le code du microcontrôleur avr.

122
répondu Matteo Caprari 2009-06-24 12:44:15

j'utilise actuellement le cadre D'essai de L'unité la plus mignonne:

http://cutest.sourceforge.net /

il est idéal pour les systèmes embarqués car il est très léger et simple. Je n'avais aucun problème à la faire fonctionner sur la plate-forme cible ainsi que sur le bureau. En plus d'écrire les tests de l'unité, tout ce qui est requis est:

  • un fichier d'en-tête inclus partout vous appelez le plus Mignon routines
  • un seul fichier " C " supplémentaire à être compilé / lié à l'image
  • un code simple ajouté au mettez en place et appelez l'unité tests-I juste ce dans une spéciale() fonction qui est compilée si UNITTEST est défini lors de la construire.

le système doit prendre en charge un tas et certaines fonctionnalités stdio (que ne possèdent pas tous les systèmes embarqués). Mais le code est assez simple pour que vous puissiez si votre plate-forme n'en a pas, il est probable que vous ayez recours à des solutions de rechange à ces exigences.

avec une utilisation judicieuse des blocs" C " externes, il supporte aussi très bien les tests C++.

39
répondu Michael Burr 2008-09-16 18:00:38

je dis presque la même chose que ratkok mais si vous avez une torsion intégrée aux tests de l'unité alors...

Unity - cadre fortement recommandé pour les essais unitaires C code.

les exemples dans le livre qui est mentionné dans ce fil de discussion TDD pour C embarqué sont écrits en utilisant L'unité (et CppUTest).

33
répondu Johan 2016-05-29 18:56:31

vous pouvez également jeter un oeil à libtap , un cadre de test C qui produit le test Anything Protocol (TAP) et s'intègre ainsi bien avec une variété d'outils sortant pour cette technologie. Il est surtout utilisé dans le monde du langage dynamique, mais il est facile à utiliser et devient très populaire.

un exemple:

#include <tap.h>

int main () {
    plan(5);

    ok(3 == 3);
    is("fnord", "eek", "two different strings not that way?");
    ok(3 <= 8732, "%d <= %d", 3, 8732);
    like("fnord", "f(yes|no)r*[a-f]$");
    cmp_ok(3, ">=", 10);

    done_testing();
}
29
répondu lsmagalhaes 2014-07-23 21:47:10

il y a un élégant cadre d'essai pour l'unité C avec support pour les objets simulés appelé cmocka . Il ne nécessite que la bibliothèque C standard, fonctionne sur une gamme de plates-formes informatiques (y compris embarquées) et avec différents compilateurs.

il a également le soutien pour différents formats de sortie de message comme la sous-unité, le protocole de Test N'importe quoi et les rapports XML de jUnit.

cmocka a été créé pour travailler également sur des plateformes intégrées et a également le soutien de Windows.

un test simple ressemble à ceci:

#include <stdarg.h>
#include <stddef.h>
#include <setjmp.h>
#include <cmocka.h>

/* A test case that does nothing and succeeds. */
static void null_test_success(void **state) {
    (void) state; /* unused */
}

int main(void) {
    const struct CMUnitTest tests[] = {
        cmocka_unit_test(null_test_success),
    };
    return cmocka_run_group_tests(tests, NULL, NULL);
}

le API est entièrement documenté et plusieurs exemples font partie du code source.

Pour commencer avec cmocka vous devriez lire l'article sur LWN.net: Unité de test avec des objets fantaisie en C

cmocka 1.0 est sorti en février 2015.

25
répondu asn 2015-02-18 08:08:37

Je n'ai pas été loin de tester une application legacy C avant de commencer à chercher un moyen de simuler des fonctions. J'avais besoin de moqueurs pour isoler le fichier C que je veux tester des autres. J'ai essayé cmock et je pense que je vais l'adopter.

Cmock scanne les fichiers d'en-tête et génère des fonctions simulées basées sur les prototypes qu'il trouve. Mock vous permettra de tester un fichier C en parfaite isolation. Tout ce que vous aurez à faire est de lier votre fichier test avec des moqueries au lieu de votre objet réel fichier.

un autre avantage de cmock est qu'il va valider les paramètres passés aux fonctions moquées, et il vous permettra de spécifier quelle valeur de retour les moqueurs devraient fournir. Ceci est très utile pour tester différents flux d'exécution dans vos fonctions.

Tests se composent des testA (), testB () typiques fonctions dans lesquelles vous construisez des attentes, fonctions d'appel pour tester et vérifier les affirmations.

la dernière étape est de générer un coureur pour vos tests avec l'unité. Cmock est lié au cadre d'essai de l'unité. L'unité est aussi facile à apprendre que n'importe quel autre cadre de test d'unité.

Bien vaut la peine d'essayer et assez facile à comprendre:

http://sourceforge.net/apps/trac/cmock/wiki

"1519170920 mise à jour" Update 1

un autre cadre sur lequel j'enquête est la parodie.

http://code.google.com/p/cmockery /

il s'agit d'un cadre C pur qui supporte les tests unitaires et les moqueries. Il ne dépend pas de ruby (contrairement à Cmock) et dépend très peu des libs externes.

il nécessite un peu plus de travail manuel pour configurer mocks parce qu'il ne fait pas de génération de code. Cela ne représente pas beaucoup de travail pour un projet existant puisque les prototypes ne changeront pas beaucoup: une fois que vous aurez vos moqueries, vous n'aurez pas besoin de les modifier pour un temps (c'est mon cas). La dactylographie supplémentaire permet un contrôle complet des moqueries. S'il y a quelque chose que vous n'aimez pas, vous changez simplement votre moquerie.

il N'est pas nécessaire d'utiliser un palonnier spécial. Vous avez seulement besoin de créer un tableau de tests et de le passer à une fonction run_tests. Un peu plus de travail manuel ici aussi, mais j'aime l'idée d'un cadre autonome.

en Plus, il contient des trucs en C que je ne connaissais pas.

la moquerie générale a besoin d'un peu plus de compréhension des moqueries pour commencer. Exemples devraient vous aider à surmonter ce. On dirait qu'il peut faire le travail avec de plus simple mécanique.

19
répondu Philippe A. 2010-07-22 18:46:26

en tant que débutant C, j'ai trouvé très utiles les diapositives intitulées développement piloté par des tests dans C . Fondamentalement, il utilise la norme assert() avec && pour délivrer un message, sans dépendances externes. Si quelqu'un est utilisé pour une pile complète framework de test, ce ne sera probablement pas le faire :)

14
répondu chelmertz 2011-10-08 23:10:25

il y a CUnit

et Embedded Unit est un cadre d'essai unitaire pour le système C intégré. Son design a été copié de JUnit et CUnit et plus, puis adapté quelque peu pour le système C intégré. L'unité embarquée ne nécessite pas de libs std. Tous les objets sont attribués à la zone const.

Et Tessy automatise les tests unitaires des logiciels embarqués.

12
répondu prakash 2008-09-15 19:27:28

Michael Plume du livre "Travailler Efficacement avec les Legacy Code" présente beaucoup de techniques spécifiques à l'unité de test au cours de C de développement.

il y a des techniques liées à l'injection de dépendances qui sont spécifiques à C et que je n'ai jamais vues ailleurs.

11
répondu Anuj Gupta 2012-12-07 21:09:00

nous avons écrit CHEAT (hébergé sur GitHub ) pour une facilité d'utilisation et de portabilité.

il n'a pas de dépendances et ne nécessite aucune installation ou configuration. Seulement un fichier d'en-tête et un cas de test est nécessaire.

#include <cheat.h>

CHEAT_TEST(mathematics_still_work,
    cheat_assert(2 + 2 == 4);
    cheat_assert_not(2 + 2 == 5);
)

les Tests sont compilés dans un exécutable qui s'occupe d'exécuter les tests et de rendre compte de leurs résultats.

$ gcc -I . tests.c
$ ./a.out
..
---
2 successful of 2 run
SUCCESS

Il a de jolies couleurs.

11
répondu Tuplanolla 2014-10-03 17:14:06

Je n'utilise pas de framework, j'utilise juste des autotools" check". Mettre en œuvre un" main " et utiliser l'assert(s).

Mon test dir Makefile.suis(s) comme:

check_PROGRAMS = test_oe_amqp

test_oe_amqp_SOURCES = test_oe_amqp.c
test_oe_amqp_LDADD = -L$(top_builddir)/components/common -loecommon
test_oe_amqp_CFLAGS = -I$(top_srcdir)/components/common -static

TESTS = test_oe_amqp
10
répondu navicore 2008-09-16 13:54:28

Cpputest - cadre fortement recommandé pour les essais unitaires C code.

les exemples dans le livre qui est mentionné dans ce thread TDD pour C sont écrits en utilisant CppUTest.

7
répondu ratkok 2011-06-07 18:46:48

j'utilise CxxTest pour l'embarqué c/c++ environnement (principalement en C++).

je préfère CxxTest parce qu'il a un script perl/python pour construire le coureur de test. Après une petite pente pour obtenir la configuration (encore plus petit puisque vous n'avez pas à écrire le coureur de test), il est assez facile à utiliser (comprend des échantillons et de la documentation utile). Le plus gros du travail a consisté à configurer le "matériel" auquel le code accède pour que je puisse effectuer des tests unitaires/modules de manière efficace. Après que il est facile d'ajouter de nouveaux scénarios de test unitaire.

comme nous l'avons mentionné précédemment, il s'agit d'un cadre d'essai unitaire C/c++. Vous aurez donc besoin d'un compilateur C++.

CxxTest Guide De L'Utilisateur Cxxtest Wiki

6
répondu Zing- 2009-11-19 09:48:28

autre que mon penchant évident

http://code.google.com/p/seatest /

est un moyen simple et agréable de tester le code Unité C. imitations xUnit

6
répondu Keith Nicholas 2010-07-01 05:09:36

après avoir lu Minunit J'ai pensé qu'une meilleure façon était de baser le test dans assert macro que j'utilise beaucoup comme technique de programme défensif. Donc j'ai utilisé la même idée de Minunit mélangé avec assert standard. Vous pouvez voir mon cadre (un bon nom pourrait être NoMinunit) dans blog de k0ga

5
répondu Roberto Vargas Caballero 2011-02-23 18:55:57
4
répondu Landon Kuhn 2008-09-15 19:22:11

Google a un cadre de test excellent. https://github.com/google/googletest/blob/master/googletest/docs/primer.md

Et oui, autant que je le vois, il travaillera avec du C, c'est à dire ne nécessite pas de fonctionnalités C++ (compilateur C++, pas sûr).

4
répondu Paweł Hajdan 2018-08-20 12:04:28

Cmockery est un projet récemment lancé qui consiste en une bibliothèque C très simple à utiliser pour l'écriture de tests unitaires.

4
répondu Alejandro Bologna 2018-08-20 12:12:08

D'abord, regardez ici: http://en.wikipedia.org/wiki/List_of_unit_testing_frameworks#C

ma société dispose d'une bibliothèque C que nos clients utilisent. Nous utilisons CxxTest (une bibliothèque de test unité C++) pour tester le code. CppUnit fonctionnera aussi. Si vous êtes coincé en C, je recommande RCUNIT (mais CUnit est bon aussi).

3
répondu Kevin 2008-09-15 20:39:24

si vous connaissez JUnit, je vous recommande CppUnit. http://cppunit.sourceforge.net/cppunit-wiki

qui suppose que vous avez un compilateur c++ pour faire les tests unitaires. si non, alors je suis d'accord avec Adam Rosenfield qu'à cocher est ce que vous voulez.

2
répondu Kwondri 2008-09-15 19:22:11

j'ai utilisé RCUNIT pour faire une unité de test de code embarqué sur le PC avant de les tester sur la cible. Une bonne abstraction de l'interface matérielle est importante, sinon l'ennui et les registres de mappage mémoire vont vous tuer.

2
répondu Gerhard 2008-11-25 11:12:08
2
répondu Tony Bai 2010-10-10 01:43:07

une technique à utiliser est de développer le code de test de l'unité avec un framework C++ xUnit (et un compilateur C++), tout en maintenant la source pour le système cible sous forme de modules C.

assurez-vous de compiler régulièrement votre source C sous votre compilateur croisé, automatiquement avec vos tests unitaires si possible.

1
répondu quamrana 2008-09-15 19:22:34

LibU ( http://koanlogic.com/libu ) dispose d'un module de test unitaire qui permet des dépendances explicites suite de test/cas, l'isolement de test, l'exécution en parallèle et un formatteur de rapport personnalisable (les formats par défaut sont xml et txt).

la Bibliothèque est sous licence BSD et contient de nombreux autres modules utiles - mise en réseau, débogage, structures de données couramment utilisées, configuration, etc. - si vous en avez besoin dans vos projets ...

1
répondu bongo 2010-04-16 08:55:58

je suis surpris que personne n'ait mentionné Cutter (http://cutter.sourceforge.net/) Vous pouvez tester C et C++, il s'intègre parfaitement avec des autotols et dispose d'un très joli tutoriel disponible.

1
répondu Kris 2013-01-22 14:48:20

API santé mentale Checker - framework de test pour les bibliothèques C/C++:

générateur automatique de tests d'Unité de base pour une bibliothèque C/C++ partagée. Il est capable de générer des données d'entrée raisonnables (dans la plupart des cas, mais malheureusement pas tous) pour les paramètres et de composer des cas de test simples ("bon état" ou "superficiel"-qualité) pour chaque fonction de l'API à travers l'analyse des déclarations dans les fichiers d'en-tête.

le la qualité des tests générés permet de vérifier l'absence d'erreurs critiques dans les cas d'utilisation simple. L'outil est capable de construire et d'exécuter les tests générés et de détecter les accidents (segfaults), les arrêts, toutes sortes de signaux émis, le code de retour de programme non-zéro et le programme suspendu.

exemples:

1
répondu aponomarenko 2015-08-17 20:10:50

dans le cas où vous ciblez les plates-formes Win32 ou le mode noyau NT, vous devriez avoir un oeil à cfix .

0
répondu Johannes Passing 2008-10-11 16:18:50

si vous êtes toujours à la recherche de cadres de test, CUnitWin32 en est un pour la plate-forme Win32/NT.

cela résout un problème fondamental que j'ai affronté avec d'autres cadres de test. À savoir les variables globales/statiques sont dans un État déterministe parce que chaque test est exécuté comme un processus séparé.

0
répondu Dushara 2009-01-12 00:30:39