和菜鸟一起深入学习国嵌实验之线程编程
1、 线程创建
代码:
#include <stdio.h> #include <string.h> #include <stdlib.h> #include <fcntl.h> #include <sys/types.h> #include <sys/stat.h> #include <unistd.h> #include <errno.h> #include <math.h> #include <pthread.h> struct member { int a; char *s; }; void *create(void *arg) { struct member *temp; temp = (struct member *)arg; printf("member->a : %d\n", temp->a); printf("member->s : %s\n", temp->s); return (void*)0; } int main(int argc, char *argv[]) { int error; pthread_t tidp; struct member *b; b= (struct member *)malloc(sizeof(struct member)); b->a = 4; b->s = "eastmoon"; error = pthread_create(&tidp, NULL, create, (void*)b); if(error) { printf("pthread is not create...\n"); return -1; } sleep(1); printf("pthread is created...\n"); return 0; }
Makefile:
CC = gcc CURTDIR = $(shell pwd) TARGET = mythread %.o:%.c $(CC)-c $(EXTRAFLAGS) $< -o $@ %.o:%.S $(CC)-c $(EXTRAFLAGS) $< -o $@ .PHONY: all clean $(TARGET): $(TARGET).o $(CC) -o $@ $^ -lpthread clean: rm-rf $(TARGET) $(TARGET).o
运行结果:
eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.1$ make gcc -c mythread.c -o mythread.o gcc -o mythread mythread.o -lpthread eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.1$ ls Makefile mypipe.txt mythread mythread.c mythread.o eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.1$ ./mythread member->a : 4 member->s : eastmoon pthread is created...
2、 线程等待
代码:
#include <stdio.h> #include <string.h> #include <stdlib.h> #include <fcntl.h> #include <sys/types.h> #include <sys/stat.h> #include <unistd.h> #include <errno.h> #include <math.h> #include <pthread.h> void *create(void *arg) { int i; for(i = 0; i < 3; i++) { sleep(2); printf("This in the thread :%d\n", i); } return NULL; } int main(int argc, char *argv[]) { pthread_t pth; int i, ret; ret = pthread_create(&pth, NULL, create, NULL); if(ret) { printf("pthread is not create...\n"); return -1; } pthread_join(pth, NULL); printf("thread was exit\n"); for(i = 0; i < 3; i++) { sleep(1); printf("This in the main: %d\n", i); } return 0; }
Makefile:
CC = gcc
CURTDIR = $(shell pwd)
TARGET = mythread_join
%.o:%.c
$(CC)-c $(EXTRAFLAGS) $< -o $@
%.o:%.S
$(CC)-c $(EXTRAFLAGS) $< -o $@
.PHONY: all clean
$(TARGET): $(TARGET).o
$(CC) -o $@ $^ -lpthread
clean:
rm-rf $(TARGET) $(TARGET).o
运行结果:
eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.2$make gcc -c mythread_join.c -o mythread_join.o gcc -o mythread_join mythread_join.o -lpthread eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.2$ls Makefile mythread_join mythread_join.c mythread_join.o eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.2$./mythread_join This in the thread :0 This in the thread :1 This in the thread :2 thread was exit This in the main: 0 This in the main: 1 This in the main: 2
总结:运行程序后,在没有调用thread_join之前线程和进程是同时运行的,调用了thread_join之后进程阻塞直到线程退出。
3、 线程退出保护设计
代码:
#include <stdio.h> #include <string.h> #include <stdlib.h> #include <fcntl.h> #include <sys/types.h> #include <sys/stat.h> #include <unistd.h> #include <errno.h> #include <math.h> #include <pthread.h> void *clean(void *arg) { printf("cleanup: %s\n", (char *)arg); return (void *)0; } void *thr_fn1(void *arg) { printf("thread 1 start \n"); pthread_cleanup_push((void *)clean, "thread 1 first handler"); pthread_cleanup_push((void *)clean, "thread 1 secondhandler"); printf("thread 1 push complete\n"); if(arg) { return (void*)1; } pthread_cleanup_pop(0); pthread_cleanup_pop(0); return (void *)1; } void *thr_fn2(void *arg) { printf("thread 2 start \n"); pthread_cleanup_push((void *)clean, "thread 2 first handler"); pthread_cleanup_push((void *)clean, "thread 2 secondhandler"); printf("thread 2 push complete\n"); if(arg) { pthread_exit((void *)2); } pthread_cleanup_pop(0); pthread_cleanup_pop(0); pthread_exit((void *)2); } int main(int argc, char *argv[]) { pthread_t tid1, tid2; int i, ret; void *tret; ret = pthread_create(&tid1, NULL, thr_fn1, (void *)1); if(ret) { printf("pthread 1 is not create...\n"); return -1; } ret = pthread_create(&tid2, NULL, thr_fn2, (void *)1); if(ret) { printf("pthread 2 is not create...\n"); return -1; } ret = pthread_join(tid1, &tret); if(ret) { printf("pthread 1 join error......\n"); return -1; } printf("thread 1 exit code %d\n", (int)tret); ret = pthread_join(tid2, &tret); if(ret) { printf("pthread 2 join error......\n"); return -1; } printf("thread 2 exit code %d\n", (int)tret); return 0; }
Makefile:
CC = gcc CURTDIR = $(shell pwd) TARGET = mythread_clean %.o:%.c $(CC)-c $(EXTRAFLAGS) $< -o $@ %.o:%.S $(CC)-c $(EXTRAFLAGS) $< -o $@ .PHONY: all clean $(TARGET): $(TARGET).o $(CC) -o $@ $^ -lpthread clean: rm-rf $(TARGET) $(TARGET).o
运行结果:
eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.3$make
gcc -c mythread_clean.c -o mythread_clean.o
gcc -o mythread_clean mythread_clean.o -lpthread
eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.3$ls
Makefile mythread_clean mythread_clean.c mythread_clean.o
eastmoon@eastmoon-virtual-machine:~/work/guoqian/3/3.3$./mythread_clean
thread 2 start
thread 2 push complete
cleanup: thread 2 second handler
cleanup: thread 2 first handler
thread 1 start
thread 1 push complete
thread 1 exit code 1
thread 2 exit code 2
总结:由运行结果可知,线程1是return退出的,所以不运行线程清理函数,而线程2是pthread_exit退出的,所以执行了线程清理函数。