acl/lib_fiber/samples/chat/reader/main.cpp
zhengshuxin 1b6d166ef6 add acl_fiber_kill for fiber lib;
add listen callback for master template.
2016-12-03 20:09:21 +08:00

181 lines
3.6 KiB
C++

#include "stdafx.h"
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include "fiber/lib_fiber.hpp"
#include "stamp.h"
#include "user_client.h"
#define STACK_SIZE 128000
static const char* __user_prefix = "reader";
static int __rw_timeout = 0;
static int __max_client = 10;
static int __cur_client = 10;
static struct timeval __begin;
static long long __total_read = 0;
static bool client_login(user_client* uc)
{
acl::string buf;
buf.format("login|%s\r\n", uc->get_name());
if (uc->get_stream().write(buf) == -1)
{
printf("login failed error, user: %s\r\n", uc->get_name());
return false;
}
if (uc->get_stream().gets(buf) == false)
{
printf("login failed, gets error %s\r\n", acl::last_serror());
return false;
}
return true;
}
static void client_logout(user_client* client)
{
client->notify_exit();
}
static void fiber_reader(user_client* client)
{
acl::socket_stream& conn = client->get_stream();
conn.set_rw_timeout(0);
if (client_login(client) == false)
{
client_logout(client);
return;
}
printf("fiber-%d: user: %s login OK\r\n", acl_fiber_self(),
client->get_name());
acl::string buf;
int max_loop = client->get_max_loop(), i;
for (i = 0; i < max_loop; ++i)
{
if (conn.gets(buf))
{
if (i <= 1)
printf("fiber-%d: gets->%s\r\n",
acl_fiber_self(), buf.c_str());
__total_read++;
continue;
}
printf("%s(%d): user: %s, gets error %s, fiber: %d\r\n",
__FUNCTION__, __LINE__, client->get_name(),
acl::last_serror(), acl_fiber_self());
break;
}
printf(">>%s(%d), user: %s, logout, loop: %d\r\n",
__FUNCTION__, __LINE__, client->get_name(), i);
client_logout(client);
}
static void fiber_client(const char* addr, const char* user, int max_loop)
{
acl::socket_stream conn;
if (conn.open(addr, 0, 0) == false)
{
printf("connect %s error %s\r\n", addr, acl::last_serror());
}
else
{
printf("fiber-%d, connect %s ok\r\n", acl_fiber_self(), addr);
user_client* client = new user_client(conn, user, max_loop);
go[=] {
fiber_reader(client);
};
client->wait_exit();
printf("--- client %s exit now ----\r\n", client->get_name());
delete client;
}
__cur_client--;
if (__cur_client == 0)
{
printf("-----All fibers over!-----\r\n");
struct timeval end;
gettimeofday(&end, NULL);
double spent = stamp_sub(&end, &__begin);
printf("---Total read: %lld, spent: %.2f, speed: %.2f---\r\n",
__total_read, spent,
(1000 * __total_read) / (spent < 1 ? 1 : spent));
acl_fiber_schedule_stop();
}
}
static void usage(const char *procname)
{
printf("usage: %s -h [help]\r\n"
" -s server_addr\r\n"
" -n max_loop\r\n"
" -c max_client\r\n"
" -r rw_timeout\r\n" , procname);
}
int main(int argc, char *argv[])
{
char addr[64];
int ch, max_loop = 100;
acl::log::stdout_open(true);
snprintf(addr, sizeof(addr), "%s", "127.0.0.1:9002");
while ((ch = getopt(argc, argv, "hs:r:c:n:")) > 0) {
switch (ch) {
case 'h':
usage(argv[0]);
return 0;
case 's':
snprintf(addr, sizeof(addr), "%s", optarg);
break;
case 'r':
__rw_timeout = atoi(optarg);
break;
case 'c':
__max_client = atoi(optarg);
break;
case 'n':
max_loop = atoi(optarg);
break;
default:
break;
}
}
__cur_client = __max_client;
gettimeofday(&__begin, NULL);
for (int i = 0; i < __max_client; i++)
{
char user[128];
snprintf(user, sizeof(user), "%s-%d", __user_prefix, i);
go[=] {
fiber_client(addr, user, max_loop);
};
}
acl::fiber::schedule();
return 0;
}