Skip to content
/ Coconut Public

Library for unit testing and debugging concurrent C/C++ programs.

License

Notifications You must be signed in to change notification settings

luksow/Coconut

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

22 Commits
 
 
 
 
 
 
 
 

Repository files navigation

Coconut

Coconut (COmpcat CONcurrency Unit Testing) is a library for testing and debugging concurrent applications in C/C++. It allows programmer to exercise selected interleavings and check some assertions. Execution with Coconut is deterministic and repeatable due to limited concurrency.

Interface

Coconut provides two interfaces: named events and named blocks. Named events are useful for debugging while named blocks are great for testing. Full documented interface can be found in src/coconut_pub.h file.

Named events

Named events allows to block certain thread by waiting for an event to be published. Events can be published by other threads. Simple example is provided below.

#include <pthread.h>
#include <stdio.h>

#include "coconut.h"

int some_var = 0;

void *thread1(void *dummy)
{
	c_wait_event("printed");
	some_var = 42;
}

void *thread2(void *dummy)
{
	printf("some_var: %d\n", some_var);
	c_assert_true(some_var == 42, "some_var != 42");
	c_publish_event("printed");
}

int main()
{
	pthread_t t1;
	pthread_t t2;

	c_init();

	pthread_create(&t1, NULL, &thread1, NULL);
	pthread_create(&t2, NULL, &thread2, NULL);
	pthread_join(t1, NULL);
	pthread_join(t2, NULL);

	c_free();

	return 0;
}

Named blocks

Named blocks allows to divide the source code into blocks and then to run them in specified order. Block of code is allowed to run only if all its predecessors finished. Simple example is provided below.

#include <pthread.h>
#include <stdio.h>

#include "coconut.h"

int some_var = 0;

void *thread1(void *dummy)
{
	c_begin_block("set");
	some_var = 42;
	c_end_block();
}

void *thread2(void *dummy)
{
	c_begin_block("print");
	printf("some_var: %d\n", some_var);
	c_assert_true(some_var == 42, "some_var != 42");
	c_end_block();
}

int main()
{
	pthread_t t1;
	pthread_t t2;

	c_init();

	// test1 - should pass
	printf("test1\n");
	some_var = 0;
	c_set_blocks_interleaving("set;print");
	pthread_create(&t1, NULL, &thread1, NULL);
	pthread_create(&t2, NULL, &thread2, NULL);
	pthread_join(t1, NULL);
	pthread_join(t2, NULL);

	// test2 - should fail
	printf("test2\n");
	some_var = 0;
	c_set_blocks_interleaving("print;set");
	pthread_create(&t1, NULL, &thread1, NULL);
	pthread_create(&t2, NULL, &thread2, NULL);
	pthread_join(t1, NULL);
	pthread_join(t2, NULL);

	c_free();

	return 0;
}

Examples

For more examples go to examples directory.

Compilation & usage

Compiling is as simple as issuing make command.

$ git clone git://github.com/luksow/Coconut.git
$ cd Coconut/src/
$ make

Make will create a static library named libcoconut.a. libcoconut.a and coconut_pub.h are the only files needed to start testing applications.

Using Coconut requires compiling application with libcoconut.a. It should be used just like a standard static library.

$ cd ../examples
$ cp ../src/libcoconut.a ./
$ cp ../src/coconut_pub.h ./coconut.h # note simplified header name
$ gcc simple_events.c libcoconut.a -lpthread -o simple_events
$ ./simple_events
some_var: 0
[simple_events.c:thread2:17]: Assert failed: some_var != 42

License

See LICENSE file.

Contact

If you have any questions, don't hesitate to contact me:

Łukasz Sowa

web: http://lukaszsowa.pl

mail: contact [at] lukaszsowa [dot] pl

About

Library for unit testing and debugging concurrent C/C++ programs.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published