#include<stdio.h>
#include<stdlib.h>
#include<pthread.h>
struct foo
{
int f_count;
pthread_mutex_t f_lock;
int f_id;
};
struct foo* foo_alloc(
int id)
{
struct foo* fp;
if((fp = (
struct foo*)
malloc(
sizeof(
struct foo))) != NULL)
{
fp->f_id = id;
fp->f_count =
1;
if(pthread_mutex_init(&fp->f_lock, NULL) !=
0)
{
free(fp);
return NULL;
}
}
return fp;
}
void foo_hold(
struct foo *fp)
{
pthread_mutex_lock(&fp->f_lock);
fp->f_count++;
pthread_mutex_unlock(&fp->f_lock);
}
void foo_rele(
struct foo *fp)
{
pthread_mutex_lock(&fp->f_lock);
if(--fp->f_count ==
0)
{
pthread_mutex_unlock(&fp->f_lock);
pthread_mutex_destroy(&fp->f_lock);
free(fp);
}
else
pthread_mutex_unlock(&fp->f_lock);
}
void printfoo(
char *str,
struct foo *fp)
{
printf(
"%s", str);
printf(
"f_count = %d\n", fp->f_count);
printf(
"f_id = %d\n", fp->f_id);
}
void* thread_func(
void *arg)
{
struct foo *fp = (
struct foo*)arg;
foo_hold(fp);
fp->f_id =
2;
foo_rele(fp);
pthread_exit(NULL);
}
int main(
void)
{
int err;
struct foo *fp;
pthread_t thid;
if((fp = foo_alloc(
1)) == NULL)
{
printf(
"foo_alloc failed\n");
exit(EXIT_FAILURE);
}
else
printf(
"foo_alloc success\n");
printfoo(
"main thread\n", fp);
err = pthread_create(&thid, NULL, thread_func, (
void*)fp);
if(err !=
0)
{
printf(
"thread_create failed\n");
exit(EXIT_FAILURE);
}
err = pthread_join(thid, NULL);
if(err !=
0)
{
printf(
"pthread_join failed\n");
exit(EXIT_FAILURE);
}
printfoo(
"after thread:\n", fp);
foo_rele(fp);
return 0;
}