static void do_destroy(RServerCtx * ctx) { if (ctx) { if (ctx->csLtr) { RServerCSLtr_Destroy(ctx->csLtr); ctx->csLtr = NULL; } if (ctx->cusEv) { evhr_cus_event_del(ctx->cusEv); ctx->cusEv = NULL; } if (ctx->evhr) { evhr_release(ctx->evhr); ctx->evhr = NULL; } if (ctx->taskPool) { tpool_destroy(ctx->taskPool); ctx->taskPool = NULL; } free(ctx); } }
struct thread_pool *tpool_create(int num_threads) { int i; struct thread_pool *tpool; if(!(tpool = calloc(1, sizeof *tpool))) { return 0; } pthread_mutex_init(&tpool->workq_mutex, 0); pthread_cond_init(&tpool->workq_condvar, 0); pthread_cond_init(&tpool->done_condvar, 0); if(num_threads <= 0) { num_threads = tpool_num_processors(); } tpool->num_threads = num_threads; if(!(tpool->threads = calloc(num_threads, sizeof *tpool->threads))) { free(tpool); return 0; } for(i=0; i<num_threads; i++) { if(pthread_create(tpool->threads + i, 0, thread_func, tpool) == -1) { /*tpool->threads[i] = 0;*/ tpool_destroy(tpool); return 0; } } return tpool; }
int tpool_release(struct thread_pool *tpool) { if(--tpool->nref <= 0) { tpool_destroy(tpool); return 0; } return tpool->nref; }
TPOOL_RTN_E tpool_create(struct tpool_ctx ** obj, uint8_t num) { int i; struct tpool_ctx * tpool = NULL; if ((tpool = malloc(sizeof(struct tpool_ctx))) == NULL) return TPOOL_FAILED; memset(tpool, 0, sizeof(struct tpool_ctx)); tpool->workers_num_total = 0; tpool->workers_num_running = 0; tpool->workers_num_working = 0; tpool->keep_alive = 0; pthread_mutex_init(&tpool->workers_num_lock, NULL); pthread_cond_init(&tpool->workers_idle_cond, NULL); pthread_mutex_init(&tpool->tasks_uid_lock, NULL); // Initial tasks if (qlist_create(&tpool->tasks) != QLIST_SUCCESS) { tpool_destroy(tpool); return TPOOL_FAILED; } // Initial workers array tpool->workers = (struct tpool_worker **) malloc(sizeof(struct tpool_worker *) * num); if (tpool->workers == NULL) { tpool_destroy(tpool); return TPOOL_FAILED; } // Initial all workers for (i = 0; i < num; i++) { if (worker_create(&tpool->workers[i]) != TPOOL_SUCCESS) { tpool_destroy(tpool); return TPOOL_FAILED; } tpool->workers[i]->uid = 0; tpool->workers[i]->tpool = tpool; tpool->workers_num_total++; } *obj = tpool; return TPOOL_SUCCESS; }
int main(int argc, const char * argv[]) { url_result_t url_r; // 结构体,主要包括all_url_list和existed_page, 用于存储爬取到的所有url。 urlq_t queue; // url队列 int num; // 用于向queue加入种子页面, queue中存储的是all_url_list中的位置 tpool_t *tpool; // 线程池 char *url_sed; // 种子网页 time_t starttime; // 起始时间 time_t endtime; // 结束时间 if (url_result_init(&url_r) == INIT_FAILURE) { printf("初始化url结果失败,退出程序\n"); exit(1); } if (queue_init(&queue) == INIT_FAILURE) { printf("初始化队列失败,退出程序\n"); exit(1); } if ((tpool = tpool_create(MAX_THREADS, &url_r, &queue)) == NULL) { printf("初始化线程池失败\n"); exit(1); } url_sed = "http://news.sohu.com/"; time(&starttime); printf("start work!\n"); // 休眠2秒,为了创造完所有的线程. sleep(2); pthread_mutex_lock(&tpool->mutex); // 首先把种子网页加入到线程中 num = url_result_add(&url_r, url_sed); queue_push(&queue, num); addStr(url_r.bloomfilter, url_sed); pthread_mutex_unlock(&tpool->mutex); pthread_cond_signal(&tpool->cond); while (queue.size > 0 || tpool->at_work != 0) { printf("queue_size: %d\n", queue.size); printf("front: %d\n", queue.front); printf("tail: %d\n", queue.tail); printf("list_size: %d\n", url_r.all_url_list_size); printf("at_work: %d\n", tpool->at_work); printf("existed_page_size: %d\n", url_r.existed_page_size); sleep(1); // 每隔1秒,输出一次日志。 } write_url_result_to_file(&url_r); tpool_destroy(); sleep(2); time(&endtime); printf("finish work"); printf("total time: %ld\n", endtime - starttime); printf("all_url_list_size: %d\n", url_r.all_url_list_size); printf("exited_page_size: %d\n", url_r.existed_page_size); return 0; }
int main() { struct web_graph webg; int i; urlq_t queue; int num; tpool_t *tpool; if (init_webg(&webg) == INIT_FAIL) { printf("初始化图失败,退出程序!\n"); exit(1); } if (queue_init(&queue) == INIT_QUEUE_FAIL) { printf("初始化队列失败,退出程序!\n"); exit(1); } if ((tpool = tpool_create(MAX_THREADS, &webg, &queue)) == NULL) { printf("初始化线程池失败!\n"); exit(1); } printf("start work!\n"); //首先要将index.html加入点集和队列中 pthread_mutex_lock(&tpool->lock); num = insert_vertex(&webg, "/techqq/index.html"); queue_push(&queue, num); pthread_mutex_unlock(&tpool->lock); pthread_cond_signal(&tpool->cond); while (queue.size > 0 || tpool->at_work != 0) { printf("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@queue_size: %d@@@@@@@@@@@@@@@@@@@@@@@\n", queue.size); printf("front: %d\n", queue.front); printf("tail: %d\n", queue.tail); printf("@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@list_size: %d@@@@@@@@@@@@@@@@@@@@@@@\n", webg.all_url_list_size); printf("$$$$$$$$$$$$$$$$$edge_set_size: %d\n", webg.edge_set_size); printf("at_work: %d\n", tpool->at_work); printf("---------------existed_page_size: %d\n", webg.existed_page_size); sleep(2); } printf("finish work!\n"); tpool_destroy(); printf("size: %d\n", webg.all_url_list_size); printf("queue_size: %d\n", queue.size); print_webg_to_file(&webg); destroy_webg(&webg); output_result_file(); }
int main(void) { int i; tpool_t test_pool; tpool_init(&test_pool, 8, 20); for ( i = 0; i < 5; i++) { tpool_add_work(test_pool, job, str[i]); } tpool_destroy(test_pool, 1); return 0; }
int main(int argc,char **argv) { printf("Http server welcome you!\n"); tpool_create(10); if(1!=argc) getoption(argc,argv);//It's hard to learn how to use it if(NULL==_log) logfd=open(DEFAULTLOG,O_WRONLY | O_APPEND | O_CREAT); else logfd=open(_log,O_WRONLY | O_CREAT | O_APPEND); daytime(); int sockfd,sockfds; if(daemon_check) daemons(); ssl_init(ctx); signal(SIGPIPE,SIG_IGN); signal(SIGCHLD, SIG_IGN); sockfd=make_socket(sockfd); sockfds=make_socket_ssl(sockfds); if(sockfd<0||sockfds<0) errorfunc("sockfd error!"); int addrlen = 1; setsockopt(sockfd,SOL_SOCKET,SO_REUSEADDR,&addrlen,sizeof(addrlen));//set the port quickly reuse setsockopt(sockfds,SOL_SOCKET,SO_REUSEADDR,&addrlen,sizeof(addrlen)); struct epoll_event events[MAXEVENTS];//question int epollfd=epoll_create(MAXEVENTS); addfd(epollfd,sockfd,0); addfd(epollfd,sockfds,0); chdir("/home/wangyao/web"); while(1) { int ret=epoll_wait(epollfd,events,MAXEVENTS,-1);//epoll func should be use in here if(ret<0) errorfunc("epoll_wait error!"); lt(events,ret,epollfd,sockfd,sockfds); } close(sockfds); close(sockfd); close(epollfd); sleep(10); tpool_destroy(); SSL_CTX_free(ctx); exit(0); }
int main(int argc, char **argv) { printf("main start...........\n"); tpool_t *tpool = tpool_create(3); if(tpool == NULL) { printf("tpool_create failed...\n"); exit(1); } size_t i = 10; size_t a[10]; for(i = 0; i < 10; i++) { a[i] = i; tpool_task_add(tpool, func, (void*)&(a[i])); } tpool_destroy(tpool); printf("main end...........\n"); return 0; }
int main() { tpool_t *t; char buf[256], *ptr; int len, i = 0; # ifdef DEBUG log_open("stderr", "tp_test", -1); # endif t = tpool_init(NULL, 3, 2, 2); printf("Thread Pool[%d] initlized OK, try to write your message after >\n", getpid()); printf("Main thread: %p\n", pthread_self()); do { printf(">"); fflush(stdout); if (!fgets(buf, sizeof(buf) - 1, stdin)) { puts("Aborted!\n"); break; } if (buf[0] == '\r' || buf[0] == '\n') continue; len = strlen(buf); buf[len - 1] = '\0'; if (!strcasecmp(buf, "quit") || !strcasecmp(buf, "exit")) { puts("Quit!\n"); break; } else if (!strcasecmp(buf, "cancel")) { for (i = 0; i < t->max_total; i++) { int cc; if (!(t->threads[i].status & TPOOL_THREAD_ACTIVED)) continue; pthread_cancel(t->threads[i].tid); } continue; } else if (!strcasecmp(buf, "cancel2")) { tpool_cancel(t); tpool_destroy(t); exit(0); } else if (!strcasecmp(buf, "timeout")) { tpool_cancel_timeout(t, 5); continue; } else if (!strcasecmp(buf, "display")) { ptr = tpool_draw(t); puts(ptr); free(ptr); continue; } ptr = strdup(buf); printf("strdup(%p)\n", ptr); tpool_exec(t, test_task, test_cancel, ptr); } while (1); //tpool_cancel(t); tpool_destroy(t); exit(0); }
int main(int argc, char *argv[]) { tpool_t *pool; logmy=log_open("test.log", 0); pool=tpool_init(10,20,1); socket_branch(); char Construction[2]; while(1) { printf("Please Input Construction number On Server:\t"); scanf("%s", Construction); printf("%s\n", Construction); switch (Construction[1]) { case 9: tpool_destroy(pool,1); log_close(logmy); pthread_exit(NULL); exit (EXIT_SUCCESS); case 8: exit (EXIT_FAILURE); case 6: break; default: break; } struct sockaddr_in client_addr; int client_addr_length =sizeof(client_addr); int new_server_socket_fd =accept(server_socket_fd,(struct sockaddr*)&client_addr, &client_addr_length); if(new_server_socket_fd < 0) { perror("Server Accept Failed:"); break; } else { printf("Accept Client Socket Address\n"); char peeraddrstr[60]; char peerip[18]; time_t timep; time(&timep); int len = sizeof(client_addr); if(!getpeername(new_server_socket_fd, (struct sockaddr *)&client_addr, &len)) { sprintf(peeraddrstr, "time: %s\npeer address: %s:%d\n\n",ctime(&timep) , inet_ntop(AF_INET, &client_addr.sin_addr, peerip, sizeof(peerip)), ntohs(client_addr.sin_port)); printf("%s\n", peeraddrstr); } tpool_add_work(pool,thread,peeraddrstr); } } sleep(5); tpool_destroy(pool,1); log_close(logmy); pthread_exit(NULL); }
/* * Given a list of directories to search, find all pools stored on disk. This * includes partial pools which are not available to import. If no args are * given (argc is 0), then the default directory (/dev/dsk) is searched. * poolname or guid (but not both) are provided by the caller when trying * to import a specific pool. */ static nvlist_t * zpool_find_import_impl(libzfs_handle_t *hdl, importargs_t *iarg) { int i, dirs = iarg->paths; struct dirent64 *dp; char path[MAXPATHLEN]; char *end, **dir = iarg->path; size_t pathleft; nvlist_t *ret = NULL; static char *default_dir = "/dev/dsk"; pool_list_t pools = { 0 }; pool_entry_t *pe, *penext; vdev_entry_t *ve, *venext; config_entry_t *ce, *cenext; name_entry_t *ne, *nenext; avl_tree_t slice_cache; rdsk_node_t *slice; void *cookie; if (dirs == 0) { dirs = 1; dir = &default_dir; } /* * Go through and read the label configuration information from every * possible device, organizing the information according to pool GUID * and toplevel GUID. */ for (i = 0; i < dirs; i++) { tpool_t *t; char *rdsk; int dfd; boolean_t config_failed = B_FALSE; DIR *dirp; /* use realpath to normalize the path */ if (realpath(dir[i], path) == 0) { (void) zfs_error_fmt(hdl, EZFS_BADPATH, dgettext(TEXT_DOMAIN, "cannot open '%s'"), dir[i]); goto error; } end = &path[strlen(path)]; *end++ = '/'; *end = 0; pathleft = &path[sizeof (path)] - end; /* * Using raw devices instead of block devices when we're * reading the labels skips a bunch of slow operations during * close(2) processing, so we replace /dev/dsk with /dev/rdsk. */ if (strcmp(path, "/dev/dsk/") == 0) rdsk = "/dev/rdsk/"; else rdsk = path; if ((dfd = open64(rdsk, O_RDONLY)) < 0 || (dirp = fdopendir(dfd)) == NULL) { if (dfd >= 0) (void) close(dfd); zfs_error_aux(hdl, strerror(errno)); (void) zfs_error_fmt(hdl, EZFS_BADPATH, dgettext(TEXT_DOMAIN, "cannot open '%s'"), rdsk); goto error; } avl_create(&slice_cache, slice_cache_compare, sizeof (rdsk_node_t), offsetof(rdsk_node_t, rn_node)); /* * This is not MT-safe, but we have no MT consumers of libzfs */ while ((dp = readdir64(dirp)) != NULL) { const char *name = dp->d_name; if (name[0] == '.' && (name[1] == 0 || (name[1] == '.' && name[2] == 0))) continue; slice = zfs_alloc(hdl, sizeof (rdsk_node_t)); slice->rn_name = zfs_strdup(hdl, name); slice->rn_avl = &slice_cache; slice->rn_dfd = dfd; slice->rn_hdl = hdl; slice->rn_nozpool = B_FALSE; avl_add(&slice_cache, slice); } /* * create a thread pool to do all of this in parallel; * rn_nozpool is not protected, so this is racy in that * multiple tasks could decide that the same slice can * not hold a zpool, which is benign. Also choose * double the number of processors; we hold a lot of * locks in the kernel, so going beyond this doesn't * buy us much. */ t = tpool_create(1, 2 * sysconf(_SC_NPROCESSORS_ONLN), 0, NULL); for (slice = avl_first(&slice_cache); slice; (slice = avl_walk(&slice_cache, slice, AVL_AFTER))) (void) tpool_dispatch(t, zpool_open_func, slice); tpool_wait(t); tpool_destroy(t); cookie = NULL; while ((slice = avl_destroy_nodes(&slice_cache, &cookie)) != NULL) { if (slice->rn_config != NULL && !config_failed) { nvlist_t *config = slice->rn_config; boolean_t matched = B_TRUE; if (iarg->poolname != NULL) { char *pname; matched = nvlist_lookup_string(config, ZPOOL_CONFIG_POOL_NAME, &pname) == 0 && strcmp(iarg->poolname, pname) == 0; } else if (iarg->guid != 0) { uint64_t this_guid; matched = nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID, &this_guid) == 0 && iarg->guid == this_guid; } if (!matched) { nvlist_free(config); } else { /* * use the non-raw path for the config */ (void) strlcpy(end, slice->rn_name, pathleft); if (add_config(hdl, &pools, path, config) != 0) config_failed = B_TRUE; } } free(slice->rn_name); free(slice); } avl_destroy(&slice_cache); (void) closedir(dirp); if (config_failed) goto error; } ret = get_configs(hdl, &pools, iarg->can_be_active); error: for (pe = pools.pools; pe != NULL; pe = penext) { penext = pe->pe_next; for (ve = pe->pe_vdevs; ve != NULL; ve = venext) { venext = ve->ve_next; for (ce = ve->ve_configs; ce != NULL; ce = cenext) { cenext = ce->ce_next; if (ce->ce_config) nvlist_free(ce->ce_config); free(ce); } free(ve); } free(pe); } for (ne = pools.names; ne != NULL; ne = nenext) { nenext = ne->ne_next; free(ne->ne_name); free(ne); } return (ret); }
int main (int argc, char **argv) { int opt = 0; /* Option Identifier */ int optindex = 0; /* Option Index */ bool isProfiling = false; /* Are we profiling the cache? */ bool isPriming = false; /* Are we priming the cache? */ long numCPUs = 0; /* The number of online CPUs */ struct dirent *dp = NULL; /* Directory Entry Pointer */ DIR *dfd = NULL; /* Directory Stream */ double loadAverages[3] = { 0.00 }; /* System Load Averages */ PGconn *pgh = NULL; /* Postgres Connection Handle */ bool isPWDRequired = false; /* Is Postgres Password Reqd? */ struct option long_options[] = /* Options for getopt() */ { {"connect-string", required_argument, NULL, 'c'}, {"profile", no_argument, NULL, 'p'}, {"prime", no_argument, NULL, 'w'}, {"data-dir", required_argument, NULL, 'D'}, {"postgres-only", no_argument, NULL, 'o'}, {"sqlite-db", required_argument, NULL, 's'}, {"help", no_argument, NULL, 'h'}, {"debug", no_argument, NULL, 'd'}, {NULL, 0, NULL, 0} }; /* Go for the glory! */ fprintf(stderr, "\n%s: Release %s - %s\n", PACKAGE_NAME, PACKAGE_VERSION, APP_RELEASE); fprintf(stderr, "\n%s\n\n", APP_COPYRIGHT); fflush(stdout); /* Process command-line options */ while ((opt = getopt_long(argc, argv, "c:s:D:awhdp", long_options, &optindex)) != -1) { switch (opt) { case 'h': usage(); exit(EXIT_SUCCESS); break; case 'p': if (isPriming == false) isProfiling = true; else { fprintf(stderr, "Profiling and warming are mutually exlusive!\n"); exit(EXIT_FAILURE); } break; case 'w': if (isProfiling == false) isPriming = true; else { fprintf(stderr, "Profiling and warming are mutually exlusive!\n"); exit(EXIT_FAILURE); } break; case 'd': is_debug = true; break; case 's': dbFileName = xstrdup(optarg); break; case 'c': pgConnectString = xstrdup(optarg); break; case 'D': pgDataDir = optarg; break; default: usage(); exit(EXIT_FAILURE); } } /* Make sure user requested profile OR prime */ if (isProfiling == false && isPriming == false) { fprintf(stderr, "Expected either -p or -w\n"); usage(); exit(EXIT_FAILURE); } /* Make sure the database name is set */ /* Get the PG log file name from the end of the command line */ if (optind < (argc - 1)) { fprintf(stderr, "too many command-line arguments (first is \"%s\")\n", argv[optind + 1]); usage(); exit(EXIT_FAILURE); } /* Perform a Postgres connection test & get password (if required) */ do { isPWDRequired = false; pgh = PQsetdbLogin(NULL, NULL, NULL, NULL, pgConnectString == NULL ? "postgres" : pgConnectString, NULL, pgPassword); if (PQstatus(pgh) == CONNECTION_BAD) { if (PQconnectionNeedsPassword(pgh) && pgPassword == NULL) { printf("\nTesting Postgres Connection\n"); PQfinish(pgh); pgPassword = simple_prompt("Password: "******"%s", "Connection Test Failed\n"); ERROR_PRINT("SQLERRMC: %s\n", PQerrorMessage(pgh)); PQfinish(pgh); exit(EXIT_FAILURE); } } } while (isPWDRequired); PQfinish(pgh); /* Get the number of available CPUs */ numCPUs = sysconf(_SC_NPROCESSORS_ONLN); if (numCPUs < 1) numCPUs = 1; /* * Choose the number of CPUs to use in the thread pool based on load * average. It only makes sense to do this if we have more than one CPU * to play with. */ if ((numCPUs > 1) && (getloadavg(loadAverages, 3) == 3)) { long idleCPUs = 0; /* The number of idle CPUs */ /* Show what we got */ printf("load averages.... %3.2f %3.2f %3.2f\n", loadAverages[0], loadAverages[1], loadAverages[2]); /* * We're going to base the number of usable CPUs by subtracting * the sum of 1 (to account for OS and I/O overhead) plus the 1 minute * load average from the number of available CPUs. */ idleCPUs = numCPUs - (1 + (int)(loadAverages[0] + 0.5)); /* Assign # of available CPUs with some sanity checking */ if (idleCPUs < numCPUs) numCPUs = idleCPUs; if (numCPUs < 1) numCPUs = 1; } /* Inform user of # of CPUs that will be used */ printf("usable CPUs...... %d\n", numCPUs); /* If we have more than one CPU, multi-thread our operations */ if (numCPUs > 1) { /* Initialize the thread pool */ thp = tpool_init(numCPUs, 1024, true); } if (isProfiling) BuildCacheProfile(); else /* isPriming */ PrimeCache(); /* If we have more than one CPU, multi-thread our operations */ if (POINTER_IS_VALID(thp)) { /* Destroy the thread pool */ tpool_destroy(thp, 1); } /* Cleanup */ free(dbFileName); return EXIT_SUCCESS; } /* main() */