示例#1
0
/* Forwards FM Packets to Shared Transport */
int fm_st_send(struct sk_buff *skb)
{
	long len;

	FMDRV_API_START();

	if (skb == NULL) {
		FM_DRV_ERR("Invalid skb, can't send");
		FMDRV_API_EXIT(-ENOMEM);
		return -ENOMEM;
	}

	/* Is anyone called without claiming FM ST? */
	if (is_fm_st_claimed == FM_ST_CLAIMED ) {
		/* Forward FM packet(SKB) to ST for the transmission */
		len = st_write(skb);
		if (len < 0) {
			/* Something went wrong in st write , free skb memory */
			kfree_skb(skb);
			FM_DRV_ERR(" ST write failed (%ld)", len);
			FMDRV_API_EXIT(-EAGAIN);
			return -EAGAIN;
		}
	} else {		/* Nobody calimed FM ST */

		kfree_skb(skb);
		FM_DRV_ERR("FM ST is not claimed, Can't send skb");
		FMDRV_API_EXIT(-EAGAIN);
		return -EAGAIN;
	}

	FMDRV_API_EXIT(0);
	return 0;
}
示例#2
0
文件: st.cpp 项目: dizel3d/disser
// read/write with call multiplexing
void task8(void* arg)
{
	static st_netfd_t rfd0 = st_open("/dev/random", O_RDONLY, S_IRUSR);
	static st_netfd_t rfd1 = st_open("/dev/urandom", O_RDONLY, S_IRUSR);
	static st_netfd_t rfd2 = st_open("/dev/zero", O_RDONLY, S_IRUSR);
	static st_netfd_t wfd = st_open("/dev/null", O_WRONLY, S_IWUSR);
	int rc = 0;
	static const int count = 10000;

	for (long i = 0; i < count; ++i) {
		if ((rc = st_read(rfd0, &rc, sizeof(rc), -1)) <= 0) {
			std::cout << "st_read " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
		if ((rc = st_read(rfd1, &rc, sizeof(rc), -1)) <= 0) {
			std::cout << "st_read " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
		if ((rc = st_read(rfd2, &rc, sizeof(rc), -1)) <= 0) {
			std::cout << "st_read " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
		if ((rc = st_write(wfd, &rc, sizeof(rc), -1)) <= 0) {
			std::cout << "st_write " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
	}
}
示例#3
0
文件: io.c 项目: 13916688528/srs
_st_netfd_t *st_accept(_st_netfd_t *fd, struct sockaddr *addr, int *addrlen, st_utime_t timeout)
{
    int osfd, err;
    _st_netfd_t *newfd;
    _st_netfd_t **p = (_st_netfd_t **) fd->aux_data;
    ssize_t n;
    char c;
    
    for ( ; ; ) {
        if (p == NULL) {
            osfd = accept(fd->osfd, addr, (socklen_t *)addrlen);
        } else {
            /* Get the lock */
            n = st_read(p[0], &c, 1, timeout);
            if (n < 0) {
                return NULL;
            }
            ST_ASSERT(n == 1);
            /* Got the lock */
            osfd = accept(fd->osfd, addr, (socklen_t *)addrlen);
            /* Unlock */
            err = errno;
            n = st_write(p[1], &c, 1, timeout);
            ST_ASSERT(n == 1);
            errno = err;
        }
        if (osfd >= 0) {
            break;
        }
        if (errno == EINTR) {
            continue;
        }
        if (!_IO_NOT_READY_ERROR) {
            return NULL;
        }
        /* Wait until the socket becomes readable */
        if (st_netfd_poll(fd, POLLIN, timeout) < 0) {
            return NULL;
        }
    }
    
    /* On some platforms the new socket created by accept() inherits */
    /* the nonblocking attribute of the listening socket */
#if defined (MD_ACCEPT_NB_INHERITED)
    newfd = _st_netfd_new(osfd, 0, 1);
#elif defined (MD_ACCEPT_NB_NOT_INHERITED)
    newfd = _st_netfd_new(osfd, 1, 1);
#else
    #error Unknown OS
#endif
    
    if (!newfd) {
        err = errno;
        close(osfd);
        errno = err;
    }
    
    return newfd;
}
示例#4
0
int _peer_connect(const peer_index_t index) {
  int client_fd, rv, result;
  struct addrinfo hints, *ai, *p;
  struct peer_info *peer_info;

  result = 0;

  memset(&hints, 0, sizeof(hints));
  hints.ai_family = PF_UNSPEC;
  hints.ai_socktype = SOCK_STREAM;

  peer_info = &peer_list[index];

  LOG("[%d] 向 Peer #%d %s:%s 建立互联\n", self_index, index, peer_info->host, peer_info->port);

  if ((rv = getaddrinfo(peer_info->host, peer_info->port, &hints, &ai)) != 0) {
    ERR("[%d] failed to getaddrinfo to peer #%d\n", self_index, index);
    return -1;
  }

  for (p = ai; p != NULL; p = p->ai_next) {
    if ((client_fd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1) {
      continue;
    }

    if ((peer_info->rpc_fd = st_netfd_open_socket(client_fd)) == NULL) {
      close(client_fd);
      continue;
    }

    if ((rv = st_connect(peer_info->rpc_fd, p->ai_addr, p->ai_addrlen, ST_UTIME_NO_TIMEOUT)) != 0) {
      st_netfd_close(peer_info->rpc_fd);
      continue;
    }

    // 写入 1 字节的 rpc 握手头
    if ((rv = st_write(peer_info->rpc_fd, (char *)&self_index, 1, ST_UTIME_NO_TIMEOUT)) == -1) {
      ERR("[%d] handshake failed.\n", self_index);
      result = -1;
    }

    break;
  }

  if (p == NULL) {
    ERR("[%d] failed to connect to peer #%d.\n", self_index, index);
    result = -1;
  }

  freeaddrinfo(ai);
  ai = NULL;
  p = NULL;


  return result;
}
示例#5
0
bool_t check_string_write(void) {

	stringer_t *output = MANAGEDBUF(1024), *strings[3] = { MANAGEDBUF(32), MANAGEDBUF(64), MANAGEDBUF(128) };

	for (int i = 0; i < 3; i++) {
		rand_write(strings[i]);
	}

	if (st_write(NULL, strings[0], strings[1], strings[2]) != 224) {
		return false;
	}

	if (st_write(output, strings[0], strings[1], strings[2]) != 224) {
		return false;
	}

	return true;

}
示例#6
0
文件: orgs.c 项目: lavabit/magma
stringer_t * org_signet_get(prime_org_signet_t *org, stringer_t *output) {

	size_t length;
	int_t written = 0;
	stringer_t *result = NULL;

	if (!org || !(length = org_signet_length(org))) {
		log_pedantic("An invalid org signet was supplied for serialization.");
		return NULL;
	}

	// See if we have a valid output buffer, or if output is NULL, allocate a buffer to hold the output.
	else if (output && (!st_valid_destination(st_opt_get(output)) || st_avail_get(output) < length)) {
		log_pedantic("An output string was supplied but it does not represent a buffer capable of holding the output.");
		return NULL;
	}
	else if (!output && !(result = st_alloc(length))) {
		log_pedantic("Could not allocate a buffer large enough to hold encoded result. { requested = %zu }", length);
		return NULL;
	}
	else if (!output) {
		output = result;
	}

	st_wipe(output);

	// Calculate the size, by writing out all the fields (minus the header) using a NULL output.
	length = st_write(NULL, prime_field_write(PRIME_ORG_SIGNET, 1, ED25519_KEY_PUB_LEN, ed25519_public_get(org->signing, MANAGEDBUF(32)), MANAGEDBUF(34)),
		prime_field_write(PRIME_ORG_SIGNET, 3, SECP256K1_KEY_PUB_LEN, secp256k1_public_get(org->encryption, MANAGEDBUF(33)), MANAGEDBUF(35)),
		prime_field_write(PRIME_ORG_SIGNET, 4, ED25519_SIGNATURE_LEN, org->signature, MANAGEDBUF(65)));

	// Then output them again into the actual output buffer, but this time include the header. This is very primitive serialization logic.
	if ((written = st_write(output, prime_header_org_signet_write(length, MANAGEDBUF(5)),
		prime_field_write(PRIME_ORG_SIGNET, 1, ED25519_KEY_PUB_LEN, ed25519_public_get(org->signing, MANAGEDBUF(32)), MANAGEDBUF(34)),
		prime_field_write(PRIME_ORG_SIGNET, 3, SECP256K1_KEY_PUB_LEN, secp256k1_public_get(org->encryption, MANAGEDBUF(33)), MANAGEDBUF(35)),
		prime_field_write(PRIME_ORG_SIGNET, 4, ED25519_SIGNATURE_LEN, org->signature, MANAGEDBUF(65)))) != (length + 5)) {
		log_pedantic("The organizational signet didn't serialize to the expected length. { written = %i }", written);
		st_cleanup(result);
		return NULL;
	}

	return output;
}
示例#7
0
文件: orgs.c 项目: lavabit/magma
/**
 * @brief	Derive an organizational signet from the corresponding private key structures.
 */
prime_org_signet_t * org_signet_generate(prime_org_key_t *org) {

	prime_org_signet_t *signet = NULL;
	stringer_t *signing = NULL, *encryption = NULL, *cryptographic = MANAGEDBUF(69);

	// Ensure the org structure contains the necessary private keys.
	if (!org || !org->encryption || !org->signing || org->signing->type != ED25519_PRIV) {
		return NULL;
	}
	else if (!(signet = mm_alloc(sizeof(prime_org_signet_t)))) {
		return NULL;
	}
	// Store the public singing, and encryption keys.
	else if (!(signing = ed25519_public_get(org->signing, NULL)) ||
		!(encryption = secp256k1_public_get(org->encryption, NULL))) {
		log_pedantic("PRIME organizational signet generation failed, the public keys could not be derived from the provided private keys.");
		org_signet_free(signet);
		st_cleanup(signing);
		return NULL;
	}

	// Generate a serialized signet with the cryptographic fields.
	else if (st_write(cryptographic, prime_field_write(PRIME_ORG_SIGNET, 1, ED25519_KEY_PUB_LEN, signing, MANAGEDBUF(34)),
		prime_field_write(PRIME_ORG_SIGNET, 3, SECP256K1_KEY_PUB_LEN, encryption, MANAGEDBUF(35))) != 69) {
		log_pedantic("PRIME organizational signet generation failed, the serialized cryptographic signet could not be derived.");
		org_signet_free(signet);
		st_free(encryption);
		st_free(signing);
		return NULL;
	}

	// Generate a signature using the serialized cryptographic fields.
	else if (!(signet->signature = ed25519_sign(org->signing, cryptographic, NULL))) {
		log_pedantic("PRIME organizational signet generation failed, the cryptographic signet signature could not be derived.");
		org_signet_free(signet);
		st_free(encryption);
		st_free(signing);
		return NULL;
	}

	// Finally, convert the serialized public keys into usable structures.
	else if (!(signet->signing = ed25519_public_set(signing)) || !(signet->encryption = secp256k1_public_set(encryption))) {
		log_pedantic("PRIME organizational signet generation failed, the serialized public keys could not be parsed.");
		org_signet_free(signet);
		st_free(encryption);
		st_free(signing);
		return NULL;
	}

	// We no longer need the serialized public keys.
	st_free(encryption);
	st_free(signing);

	return signet;
}
示例#8
0
int peer_request(const char *peer_name, const char *method, const char *parameter) {
  static uint8_t request_id = 0;

  LOG("[%d] 准备发出一次 RPC 请求,目标结点:%s,方法:%s,参数:%s\n", self_index, peer_name, method, parameter);

  peer_index_t dest_index;
  struct peer_info *peer_info;
  int i, len, matched;

  for (dest_index = 0; dest_index < peer_count; dest_index ++) {
    if (dest_index != self_index) {
      peer_info = &peer_list[dest_index];
      len = strlen(peer_info->name);
      matched = 1;

      for (i = 0; i < len; i++) {
        if (peer_info->name[i] != peer_name[i]) {
          matched = 0;
          break;
        }
      }

      if (matched == 0) continue;

      // 匹配到结点对应的 dest_index,构造 RPC 业务包并准备发送
      struct rpc_package_head *head;
      char *data;

      head = protocol_package_create(REQUEST, self_index, dest_index, request_id++, method, parameter);

      rpcpkg_len pkg_len, cursor;

      data = protocol_encode(head, &cursor);

      // 释放结构体
      protocol_package_free(head);
      head = NULL;

      // 发送缓冲区包内容
      if ((pkg_len = st_write(peer_info->rpc_fd, data, cursor, ST_UTIME_NO_TIMEOUT)) != cursor) {
        ERR("[%d] 写入 RPC 包长度 %d 与原包长 %d 不符,错误信息:%s\n", self_index, pkg_len, cursor, strerror(errno));
      }

      free(data);
      data = NULL;

      return cursor;
    }
  }

  return 0;
}
示例#9
0
文件: st.cpp 项目: dizel3d/disser
// read/write without call multiplexing
void task7(void* arg)
{
	static st_netfd_t wfd = st_open("/dev/null", O_WRONLY, S_IWUSR);
	int rc = 0;
	static const int count = 40000;

	for (long i = 0; i < count; ++i) {
		if ((rc = st_write(wfd, &rc, sizeof(rc), -1)) <= 0) {
			std::cout << "st_write " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
	}
}
示例#10
0
文件: SMUSync.cpp 项目: sue602/st-nvs
bool SMUSync::PacketWebService(st_netfd_t fd, const char* status_code, const std::vector<SyncPlatformDataResult>& result)
{

	std::string body;
	std::string head;
	std::string msg;
	{
		if(result.size() != 0)
		{
			DMXml xml;
			
			xml.NewRoot("SyncResponseResult");
			for(int i =0;i<result.size();i++)
			{
				xml.NewChild("SyncResult",0)->NewChild("StreamNo",result[i].SerialNumber.c_str())->GetParent()
					->NewChild("Result", result[i].ErrCode.c_str())->GetParent()
					->NewChild("Descr", result[i].Desc.c_str())->GetParent()
					->NewChild("OPFlag",result[i].UserState.c_str())->GetParent()
					->NewChild("ViewerName",result[i].ViewName.c_str())->GetParent();
				xml.GetParent();
			}
			body = xml.Encode();
		}
		else
		{
			body = "<body>This is HMSyncPlatformServer, Is Running!</body>";
		}
	}


	char body_len[10] = {};
	sprintf_s(body_len, " %d\r\n",body.length());

	head = "HTTP/1.1 ";
	head.append(status_code);
	head.append("\r\n");
	head.append("Server: HMSyncPlatformServer\r\n");
	head.append("Content-Type: text/html\r\n");
	head.append("Accept-Ranges: byte\r\n");
	head.append("Connection: close\r\n");
	head.append("Content-Length: ");
	head.append(body_len);
	head.append("\r\n");

	msg.append(head);
	msg.append(body);

	st_write(fd, msg.c_str(), msg.length()+1, -1);
	return true;
}
示例#11
0
/****************************************************************************
 * Function             - st_wdt_write_test
 * Functionality        - This function recieves the test params and calls
 *                        the write
 * Input Params         -  info,test_id
 * Return Value         -  0: SUCCESS, -1: FAILURE
 * Note                 -  None
 ****************************************************************************/
int st_wdt_write_test(struct st_wdt_testparams *info, char *test_id, int fileDesc)
{
	int result = SUCCESS;
	int retVal = 0;

	do {
		retVal = st_write(fileDesc, "C\0", ST_WDT_WRITEBUFF_LEN);
		if (FAILURE == retVal) {
			TEST_PRINT_ERR("file write failed ");
			result = FAILURE;
		}
	} while (0);
	return result;
}
示例#12
0
文件: orgs.c 项目: lavabit/magma
stringer_t * org_signet_fingerprint(prime_org_signet_t *org, stringer_t *output) {

	stringer_t *holder = MANAGEDBUF(134);

	if (!org || !org->signing || !org->encryption || !org->signature || st_length_get(org->signature) != 64) {
		return false;
	}
	else if (st_write(holder, prime_field_write(PRIME_ORG_SIGNET, 1, ED25519_KEY_PUB_LEN, ed25519_public_get(org->signing, MANAGEDBUF(32)), MANAGEDBUF(34)),
		prime_field_write(PRIME_ORG_SIGNET, 3, SECP256K1_KEY_PUB_LEN, secp256k1_public_get(org->encryption, MANAGEDBUF(33)), MANAGEDBUF(35)),
		prime_field_write(PRIME_ORG_SIGNET, 4, ED25519_SIGNATURE_LEN, org->signature, MANAGEDBUF(65))) != 134) {
		return false;
	}

	return hash_sha512(holder, output);
}
示例#13
0
文件: io.c 项目: dashaomai/CStudy
void *handle_conn(void *arg) {
  st_netfd_t client;
  client = (st_netfd_t)arg;
  arg = NULL;

  char buff[1024];
  int len = sizeof(buff) / sizeof(buff[0]);

  int received;

  received = st_read(client, buff, len, ST_UTIME_NO_TIMEOUT);

  // fprintf(stdout, "%s\n", buff);
  st_netfd_t STDOUT;
  STDOUT = st_netfd_open(STDOUT_FILENO);

  st_write(STDOUT, buff, sizeof(buff), ST_UTIME_NO_TIMEOUT);

  received = st_write(client, buff, received, ST_UTIME_NO_TIMEOUT);

  st_netfd_close(client);

  return 0;
}
示例#14
0
文件: SMUSync.cpp 项目: sue602/st-nvs
bool SMUSync::LoginPlat(st_netfd_t fd, const PlatLoginInfo& plat)
{
	DMXml xml;
	bool flag = true;
	std::string msg;
	char		RecvBuf[2048] = {};
	UINT32      RecvLen = 0;

	xml.NewRoot("soap:Envelope")
		->SetTextAttribute("xmlns:soap", "http://www.w3.org/2003/05/soap-envelope")
		->SetTextAttribute("xmlns:xsi", "http://www.w3.org/2001/XMLSchema-instance")
		->SetTextAttribute("xmlns:xsd", "http://www.w3.org/2001/XMLSchema")
		->SetTextAttribute("xmlns:soapenc", "http://schemas.xmlsoap.org/soap/encoding/")
		->NewChild("soap:Body", 0)
		->NewChild("Authenticate", 0)
		->SetTextAttribute("xmlns","http://see1000.com/service")
		->NewChild("name", plat.PlatUserName.c_str())->GetParent()
		->NewChild("pass", plat.PlatPwd.c_str());
	std::string body = xml.Encode();

	//PacketPlatServer("Authenticate", body);

	do 
	{
		if (st_write(fd, msg.c_str(), msg.length(),-1)<0)
		{
			flag = true;
			break;
		}

		if (st_read(fd, RecvBuf, 2048, -1)<0)
		{
			flag = false;
			break;
		}

	/*	{
			std::string result = ParseWebService(RecvBuf, "AuthenticateResult");
			if(result.compare("true"))
			{
				return false;
			}
		}*/

	} while (0);

	return flag;
}
示例#15
0
hoxResult
hoxSocketAPI::write_string( const st_netfd_t    nfd,
                            const std::string&  sData )
{
    const int nSize = sData.size();

    if ( nSize != st_write( nfd,
                            sData.c_str(), nSize,
                            ST_UTIME_NO_TIMEOUT ) )
    {
        hoxLog(LOG_SYS_WARN, "%s: Failed to write using st_write", __FUNCTION__);
        return hoxRC_ERR;
    }

    return hoxRC_OK;
}
示例#16
0
文件: orgs.c 项目: lavabit/magma
bool_t org_signet_verify(prime_org_signet_t *org) {

	stringer_t *holder = MANAGEDBUF(69);

	if (!org || !org->signing || !org->encryption || !org->signature || st_length_get(org->signature) != 64) {
		return false;
	}
	else if (st_write(holder, prime_field_write(PRIME_ORG_SIGNET, 1, ED25519_KEY_PUB_LEN, ed25519_public_get(org->signing, MANAGEDBUF(32)), MANAGEDBUF(34)),
		prime_field_write(PRIME_ORG_SIGNET, 3, SECP256K1_KEY_PUB_LEN, secp256k1_public_get(org->encryption, MANAGEDBUF(33)), MANAGEDBUF(35))) != 69) {
		return false;
	}
	else if (ed25519_verify(org->signing, holder, org->signature)) {
		return false;
	}

	return true;
}
示例#17
0
文件: st.cpp 项目: dizel3d/disser
void task15(void* arg)
{
	st_netfd_t rfd = st_open("/Users/vss/projects/1.gz", O_RDONLY, S_IRUSR);
	st_netfd_t wfd = st_open("/Users/vss/projects/tmp.gz", O_WRONLY, S_IWUSR);

	for (long w = 0; w < 3; ++w) {
		char buffer[32096];
		const char str[] = "Of course, take it!";
		char response[1024 + sizeof(str)];
		int rc = 0;

		int c = 0;
		while (c < sizeof(buffer))
		{
			if ((rc = st_read(rfd, buffer + c, std::min<int>(4, sizeof(buffer) - c), -1)) <= 0) {
				std::cout << "st_read " << rc << " " << strerror(rc) << std::endl;
				exit(1);
			}
			c += rc;
		}

		if ((rc = st_mutex_lock(test4_mutex)) != 0) {
			std::cout << "st_mutex_lock " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}

		for (int i = 0; i < sizeof(response); i += sizeof(str))
		{
			memcpy(response + i, str, sizeof(str));
		}

		if ((rc = st_mutex_unlock(test4_mutex)) != 0) {
			std::cout << "st_mutex_unlock " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}

		if ((rc = st_write(wfd, response, sizeof(response), -1)) <= 0) {
			std::cout << "st_write " << rc << " " << strerror(rc) << std::endl;
			exit(1);
		}
	}

	st_netfd_close(rfd);
	st_netfd_close(wfd);
}
int SrsSocket::write(const void* buf, size_t size, ssize_t* nwrite)
{
    int ret = ERROR_SUCCESS;
    
    *nwrite = st_write(stfd, (void*)buf, size, send_timeout);
    
    if (*nwrite <= 0) {
		if (errno == ETIME) {
			return ERROR_SOCKET_TIMEOUT;
		}
		
        return ERROR_SOCKET_WRITE;
    }
    
    send_bytes += *nwrite;
        
    return ret;
}
示例#19
0
文件: test.c 项目: zgbkny/ctoolx
/*
 * Session handling function stub. Just dumps small HTML page.
 */
void handle_session(long srv_socket_index, st_netfd_t cli_nfd)
{
  static char resp[] = "HTTP/1.0 200 OK\r\nContent-type: text/html\r\n"
                       "Connection: close\r\n\r\n<H2>It worked!</H2>\n";
  char buf[512];
  int n = sizeof(resp) - 1;
  struct in_addr *from = st_netfd_getspecific(cli_nfd);

  if (st_read(cli_nfd, buf, sizeof(buf), SEC2USEC(REQUEST_TIMEOUT)) < 0) {
    err_sys_report(errfd, "WARN: can't read request from %s: st_read",
		   inet_ntoa(*from));
    return;
  }
  if (st_write(cli_nfd, resp, n, ST_UTIME_NO_TIMEOUT) != n) {
    err_sys_report(errfd, "WARN: can't write response to %s: st_write",
		   inet_ntoa(*from));
    return;
  }

  RQST_COUNT(srv_socket_index)++;
}
示例#20
0
int SrsStSocket::write(void* buf, size_t size, ssize_t* nwrite)
{
    int ret = ERROR_SUCCESS;

    ssize_t nb_write = st_write(stfd, buf, size, send_timeout);
    if (nwrite) {
        *nwrite = nb_write;
    }

    // On success a non-negative integer equal to nbyte is returned.
    // Otherwise, a value of -1 is returned and errno is set to indicate the error.
    if (nb_write <= 0) {
        // @see https://github.com/simple-rtmp-server/srs/issues/200
        if (nb_write < 0 && errno == ETIME) {
            return ERROR_SOCKET_TIMEOUT;
        }

        return ERROR_SOCKET_WRITE;
    }

    send_bytes += nb_write;

    return ret;
}
示例#21
0
void *_peer_task_worker(void *arg) {
  struct rpc_package_head *task;
  task = (struct rpc_package_head*)arg;
  arg = NULL;

  LOG("[%d] 处理一个 %d -> %d 的RPC 业务 #%d\n", self_index, task->source, task->destination, task->id);

  // TODO: 编写业务的通用处理办法
  struct rpc_package_head *response;
  response = protocol_package_create(RESPONSE, task->destination, task->source, task->id, "任务完成!Mission Completeion!", NULL);

  rpcpkg_len pkg_len, sended;
  char *data;
  struct  peer_info *peer_info;

  peer_info = &peer_list[response->destination];

  data = protocol_encode(response, &pkg_len);

  protocol_package_free(response);
  response = NULL;

  if ((sended = st_write(peer_info->rpc_fd, data, pkg_len, ST_UTIME_NO_TIMEOUT)) != pkg_len) {
    ERR("[%d] 写回 RPC 包长度 %d 与原包长 %d 不符,错误信息:%s\n", self_index, sended, pkg_len, strerror(errno));
  }

  free(data);
  data = NULL;

  // 清理和结束
  protocol_package_free(task);
  task = NULL;

  worker_thread_count --;
  return 0;
}
示例#22
0
static void *handle_request(void *arg)
{
  struct pollfd pds[2];
  st_netfd_t cli_nfd, rmt_nfd;
  int sock, n;
  char buf[IOBUFSIZE];

  cli_nfd = (st_netfd_t) arg;
  pds[0].fd = st_netfd_fileno(cli_nfd);
  pds[0].events = POLLIN;

  /* Connect to remote host */
  if ((sock = socket(PF_INET, SOCK_STREAM, 0)) < 0) {
    print_sys_error("socket");
    goto done;
  }
  if ((rmt_nfd = st_netfd_open_socket(sock)) == NULL) {
    print_sys_error("st_netfd_open_socket");
    close(sock);
    goto done;
  }
  if (st_connect(rmt_nfd, (struct sockaddr *)&rmt_addr,
		 sizeof(rmt_addr), -1) < 0) {
    print_sys_error("st_connect");
    st_netfd_close(rmt_nfd);
    goto done;
  }
  pds[1].fd = sock;
  pds[1].events = POLLIN;

  /* Now just pump the data through */
  for ( ; ; ) {
    pds[0].revents = 0;
    pds[1].revents = 0;

    if (st_poll(pds, 2, -1) <= 0) {
      print_sys_error("st_poll");
      break;
    }

    if (pds[0].revents & POLLIN) {
      if ((n = (int) st_read(cli_nfd, buf, IOBUFSIZE, -1)) <= 0)
        break;
      if (st_write(rmt_nfd, buf, n, -1) != n)
        break;
    }

    if (pds[1].revents & POLLIN) {
      if ((n = (int) st_read(rmt_nfd, buf, IOBUFSIZE, -1)) <= 0)
        break;
      if (st_write(cli_nfd, buf, n, -1) != n)
        break;
    }
  }
  st_netfd_close(rmt_nfd);

done:

  st_netfd_close(cli_nfd);

  return NULL;
}
示例#23
0
void *probe(void *data) 
{ 
  int sock, len;
  struct sockaddr_in rmt;
  st_netfd_t rmt_nfd;
  struct probedef *probe = (struct probedef *)data;
  char buffer[1024];
  st_utime_t start;

  ST_INITIATE(110);

  start = st_utime();

  if (debug > 3) fprintf(stderr, "Connecting to: %s\n", probe->ipaddress);
  if (st_connect(rmt_nfd, (struct sockaddr *)&rmt, sizeof(rmt), TIMEOUT) < 0) {
    char buf[256];

    sprintf(buf, "%s(%d): %s", probe->ipaddress, __LINE__, strerror(errno));
    probe->connect = ((float) (st_utime() - start)) * 0.000001;
    probe->msg = strdup(buf);
    LOG(LOG_DEBUG, probe->msg);
    if (debug > 3) fprintf(stderr, "%s: %s\n", probe->ipaddress, probe->msg);
    goto err_close;
  }
  probe->connect = ((float) (st_utime() - start)) * 0.000001;

  // expect here: +OK POP3 xxx.xxxxxxx.xx v2000.70rh server ready
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("read", TIMEOUT);
    goto err_close;
  }
  if (debug > 3) fprintf(stderr, "< %s", buffer);
  if (buffer[0] != '+') {
    probe->msg = strdup(buffer);
    goto err_close;
  }
  if (probe->username == NULL || probe->username[0] == 0) {
    probe->msg = strdup("missing username");
    goto err_close;
  }

  sprintf(buffer, "USER %s\n", probe->username);
  if (debug > 3) fprintf(stderr, "> %s", buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("write", TIMEOUT);
    goto err_close;
  }

  // expect here: +OK User name accepted, password please
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("read", TIMEOUT);
    goto err_close;
  }
  if (debug > 3) fprintf(stderr, "< %s", buffer);
  if (buffer[0] != '+') {
    probe->msg = strdup(buffer);
    goto err_close;
  }

  sprintf(buffer, "PASS %s\n", probe->password);
  if (debug > 3) fprintf(stderr, "> %s", buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("write", TIMEOUT);
    goto err_close;
  }

  // expect here: +OK Mailbox open, 62 messages
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("read", TIMEOUT);
    goto err_close;
  }
  if (debug > 3) fprintf(stderr, "< %s", buffer);
  if (buffer[0] != '+') {
    probe->msg = strdup(buffer);
    goto err_close;
  }

  sprintf(buffer, "QUIT\n");
  if (debug > 3) fprintf(stderr, "> %s", buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("write", TIMEOUT);
    goto err_close;
  }

  // expect here: +OK Sayonara
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    ST_ERROR("read", TIMEOUT);
    goto err_close;
  }
  if (debug > 3) fprintf(stderr, "< %s", buffer);
  if (buffer[0] != '+') {
    probe->msg = strdup(buffer);
    goto err_close;
  }

err_close:
  st_netfd_close(rmt_nfd);
  probe->total = ((float) (st_utime() - start)) * 0.000001;

done:
  thread_count--;
  return NULL;
}
/*---------------------------------------------------------------------------
 *
 *--------------------------------------------------------------------------*/
int 
send_scsi_command(char *buffer, scsi_command_t *s, int cmd_id) 
{
#ifdef DIXTRAC_LINUX_SG

  int cmd_len,status = 0;

#ifdef LINUX_SG_IO
  sg_io_hdr_t sgio_hdr;
#else
  uint in_size,out_size;
  struct sg_header *sg_hd;
  char *buf_pointer;
#endif

#ifndef SG_TIMER  
  struct timeval start;
  struct timezone tz;
#endif


#ifdef WRITE_CHECK
  assert((s->command.opcode!=WRITE_6) && (s->command.opcode!=WRITE_10));
#endif

  cmd_len = s->length;

  /* safety checks */
  if (!cmd_len) return -1;            /* need a cmd_len != 0 */
  if (!buffer) return -1;             /* check argument to be != NULL */

/*   printf("SCSI command 0x%2X: length %d, datalen %d\n",s->command.opcode, */
/* 	 s->length,s->datalen); */

#ifdef LINUX_SG_IO
  memset((void *) &sgio_hdr, 0, sizeof(sg_io_hdr_t));
  sgio_hdr.interface_id = 'S';
  sgio_hdr.cmd_len = cmd_len;
  sgio_hdr.iovec_count = 0;
  sgio_hdr.mx_sb_len = sizeof(sense_buffer);
  if (scsi_command_type (s->command.opcode) == SCSI_DATA_IN) 
    sgio_hdr.dxfer_direction = SG_DXFER_FROM_DEV;
  else
    sgio_hdr.dxfer_direction = SG_DXFER_TO_DEV;
  sgio_hdr.dxfer_len = s->datalen;
  sgio_hdr.dxferp = (void *) buffer;
  sgio_hdr.cmdp = (unsigned char *) &(s->command);
  sgio_hdr.sbp = (unsigned char *) sense_buffer;
  sgio_hdr.timeout = SG_IO_TIMEOUT;
  sgio_hdr.pack_id = cmd_id;
  sgio_hdr.flags = SG_FLAG_DIRECT_IO; 
#else
  /* adjust pointer to buffer passed to write so that we can prepend the 
     data in buffer with the SCSI command                                */
  buf_pointer = buffer - cmd_len;
  /* copy the command */
  memcpy(buf_pointer,(char *) &s->command,s->length );
  
  if (scsi_command_type (s->command.opcode) == SCSI_DATA_IN) {
    in_size = 0;
    out_size = s->datalen;
  }
  else {
    in_size = s->datalen;
    out_size = 0;
    /* copy the additional data to be sent */
    /* memcpy(in_buffer + SCSI_OFFSET + s->length,buffer,in_size); */
  }
  /* make sure we are sending at most # of bytes handled by sg driver */
  if (SG_HDR_OFFSET + cmd_len + in_size > SG_BIG_BUFF) return -1;
 
  if (SG_HDR_OFFSET + out_size > SG_BIG_BUFF) {
    out_size = SG_BIG_BUFF-SG_HDR_OFFSET;
    /*
    printf("exec_scsi_command: Warning - can retrieve only %d KB of data\n",
	   out_size / 1024);
    */
  }
  /* make buf_pointer point to the begining of the buffer given to write */
  buf_pointer -= SG_HDR_OFFSET;

  /* generic SCSI device header construction */
  sg_hd = (struct sg_header *) buf_pointer;
  sg_hd->reply_len   = SG_HDR_OFFSET + out_size;
  sg_hd->twelve_byte = (cmd_len == 12);
  sg_hd->pack_id = cmd_id; 
  sg_hd->result = 0;
#endif

#ifndef SG_TIMER  
  gettimeofday(&start,&tz);
#endif

#ifdef LINUX_SG_IO
  /* send command */
#ifdef STATE_THREADS
  status = st_write(scsidev_fd, &sgio_hdr, sizeof(sg_io_hdr_t),ST_TIMEOUT);
#else
  status = write(scsidev_fd, &sgio_hdr, sizeof(sg_io_hdr_t));
#endif
  if ( status < 0 || (status < sizeof(sg_io_hdr_t))) {
    /* some error happened */
    fprintf( stderr, "write(sg_io) result = 0x%x cmd = 0x%x\n",
	     status, s->command.opcode );
  }
#else
  /* send command */
  status = write(scsidev_fd, buf_pointer, SG_HDR_OFFSET + cmd_len + in_size);
  if ( status < 0 || status != SG_HDR_OFFSET + cmd_len + in_size ||
       sg_hd->result ) {
    /* some error happened */
    fprintf( stderr, "write(generic) result = 0x%x cmd = 0x%x\n",
	     sg_hd->result, s->command.opcode );
  }
#endif

#ifdef SG_TIMER

  //  printf("%s() (%d,%d)\n", __func__, sgio_hdr.duration.tv_sec,
  //	 sgio_hdr.duration.tv_usec);

#ifdef LINUX_SG_IO
  ustart = sgio_hdr.duration.tv_usec;
  ustart_sec = sgio_hdr.duration.tv_sec;
#else
  ustart = sg_hd->time.tv_usec;
  ustart_sec = sg_hd->time.tv_sec;
#endif
#else 
  ustart = start.tv_usec;
  ustart_sec = start.tv_sec;
#endif  

  return status;

/* DIXTRAC_LINUX_SG */
#endif

#ifdef DIXTRAC_FREEBSD_CAM
  union ccb ccb;
  int flags;
  int rc;
  char cmd_spec[30];

  struct timeval start;
  struct timeval stop;
  struct timezone tz;
  
  flags = (scsi_command_type (s->command.opcode) == 
	   SCSI_DATA_IN) ? CAM_DIR_IN : CAM_DIR_OUT;

  ccb.ccb_h.path_id = cam_device.path_id;
  ccb.ccb_h.target_id = cam_device.target_id;
  ccb.ccb_h.target_lun = cam_device.target_lun;

  /* The following command must be included to make CAM work */
  sprintf(cmd_spec,"");
  for(rc=0;rc<s->length;rc++) {
    sprintf(cmd_spec,"%s v",cmd_spec);
  }

  csio_build(&ccb.csio,
	     /* data_ptr */ buffer,
	     /* dxfer_len */ s->datalen,
	     /* flags */ flags | CAM_DEV_QFRZDIS,
	     /* retry_count */ 0,
	     /* timeout */ 5000, 
	     /* cmd_spec...*/ cmd_spec, 
	     ((char *) &s->command)[0],((char *) &s->command)[1],
	     ((char *) &s->command)[2],((char *) &s->command)[3],
	     ((char *) &s->command)[4],((char *) &s->command)[5],
	     ((char *) &s->command)[6],((char *) &s->command)[7],
	     ((char *) &s->command)[8],((char *) &s->command)[9],
	     ((char *) &s->command)[10],((char *) &s->command)[11],
	     ((char *) &s->command)[12],((char *) &s->command)[13],
	     ((char *) &s->command)[14],((char *) &s->command)[15]
);

  gettimeofday(&start,&tz);
  ustart = start.tv_usec;
  ustart_sec = start.tv_sec;

  rc = cam_send_ccb(&cam_device, &ccb);

  gettimeofday(&stop,&tz);
  ustop_sec = stop.tv_sec;
  ustop = stop.tv_usec;

  if (rc < 0 || 
      (ccb.ccb_h.status & CAM_STATUS_MASK) != CAM_REQ_CMP) {
    fprintf(stderr, "Error: cam_send_ccb (rc=%d)\n", rc);

    if ((ccb.ccb_h.status & CAM_STATUS_MASK) == CAM_SCSI_STATUS_ERROR) {
      fprintf(stderr, "Printing sense buffer\n");
      scsi_sense_print(&cam_device, &ccb.csio, stderr);
    }
    return -1;
  }

  return 0;

/* DIXTRAC_FREEBSD_CAM */
#endif
}
示例#25
0
int pushto(st_netfd_t rmt_nfd, struct thr_data *td)
{
  FILE *in;
  char buffer[BUFSIZ];
  struct stat st;
  int filesize;
  int i, len;
  struct q_info *q = td->q;
  char *basename;
  
  if ((basename = strrchr(td->filename, '/')) == NULL) {
    basename = td->filename;
  } else {
    basename++;
  }
  if (stat(td->filename, &st)) {
    LOG(LOG_WARNING, "%s: %m", td->filename);
    return 0;
  }
  filesize = (int) st.st_size;
  if (filesize == 0) {
    LOG(LOG_WARNING, "zero size: %s", td->filename);
    return 1;
  }

  // expect: +OK UpWatch Acceptor vx.xx. Please login
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading login request string"); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  if (buffer[0] != '+') {
    LOG(LOG_WARNING, buffer);
    return 0;
  } 

  sprintf(buffer, "USER %s\n", q->user);
  uw_setproctitle("%s:%d %s", q->host, q->port, buffer);
  if (debug > 3) fprintf(stderr, "%s[%u] > %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout writing %s", buffer); 
    } else { 
      LOG(LOG_WARNING, "write: %m"); 
    }
    return 0;
  }

  // expect here: +OK Please enter password
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading OK enter password"); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  if (buffer[0] != '+') {
    LOG(LOG_WARNING, buffer);
    return 0;
  } 

  sprintf(buffer, "PASS %s\n", q->pwd);
  uw_setproctitle("%s:%d PASS xxxxxxxx", q->host, q->port);
  if (debug > 3) fprintf(stderr, "%s[%u] > %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout writing %s", buffer); 
    } else { 
      LOG(LOG_WARNING, "write: %m"); 
    }
    return 0;
  }

  // expect here: +OK logged in, enter command
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading enter command"); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  if (buffer[0] != '+') {
    LOG(LOG_WARNING, buffer);
    return 0;
  } 

  sprintf(buffer, "DATA %d %s\n", filesize, basename);
  uw_setproctitle("%s:%d %s", q->host, q->port, buffer);
  if (debug > 3) fprintf(stderr, "%s[%u] > %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout writing %s", buffer); 
    } else { 
      LOG(LOG_WARNING, "write: %m"); 
    }
    return 0;
  }

  // expect here: +OK start sending your file
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading DATA response"); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  if (buffer[0] != '+') {
    LOG(LOG_WARNING, buffer);
    return 0;
  } 

  if ((in = fopen(td->filename, "r")) == NULL) {
    LOG(LOG_ERR, "can't open %s", td->filename);
    return 0;
  }

  uw_setproctitle("%s:%d: UPLOADING, size=%u %s", q->host, q->port,
                filesize, td->filename);
  while ((i = fread(buffer, 1, sizeof(buffer), in)) == sizeof(buffer)) {
    //LOG(LOG_DEBUG, "read %d from input", i);
    len = st_write(rmt_nfd, buffer, i, TIMEOUT);
    if (len == -1) {
      if (errno == ETIME) { 
        LOG(LOG_WARNING, "timeout writing %s", buffer); 
      } else { 
        LOG(LOG_WARNING, "write: %m"); 
      }
      fclose(in);
      return 0;
    }
    //LOG(LOG_DEBUG, "written %d to output", len);
  }

  if (!feof(in)) {
    LOG(LOG_ERR, "fread: %m");
    fclose(in);
    return 0;
  }
  if (i>0 && st_write(rmt_nfd, buffer, i, TIMEOUT) != i) {
    LOG(LOG_ERR, "socket write error: %m");
    fclose(in);
    return 0;
  }
  fclose(in);

  // expect here: +OK Thank you. Enter command
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading enter command"); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  if (buffer[0] != '+') {
    LOG(LOG_WARNING, buffer);
    return 0;
  } 

  sprintf(buffer, "QUIT\n");
  uw_setproctitle("%s:%d %s", q->host, q->port, buffer);
  if (debug > 3) fprintf(stderr, "%s[%u] > %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  len = st_write(rmt_nfd, buffer, strlen(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout writing %s", buffer); 
    } else { 
      LOG(LOG_WARNING, "write: %m"); 
    }
    return 0;
  }

  // expect here: +OK Nice talking to you. Bye
  memset(buffer, 0, sizeof(buffer));
  len = st_read(rmt_nfd, buffer, sizeof(buffer), TIMEOUT);
  if (len == -1) {
    if (errno == ETIME) { 
      LOG(LOG_WARNING, "timeout reading QUIT response", buffer); 
    } else { 
      LOG(LOG_WARNING, "read: %m"); 
    }
    return 0;
  }
  if (debug > 3) fprintf(stderr, "%s[%u] < %s", q->host, st_netfd_fileno(rmt_nfd), buffer);
  return 1;
}
示例#26
0
文件: rpc.c 项目: dashaomai/CStudy
static void *link_to_peers(void *arg) {
  int client_fd, index, rv;
  st_netfd_t client;
  struct addrinfo hints, *ai, *p;
  const char *host = "0.0.0.0";

  fprintf(stderr, "link to perrs\n");

  for (int i=0; i<vp_count; i++) {
    if (i == my_index) continue;
    char port[16];

    //snprintf(port, 16 - 1, "%d", RPC_PORT + i);
    index = RPC_PORT + i;
    sprintf(port, "%d", index);

    memset(&hints, 0, sizeof(hints));
    hints.ai_family = PF_UNSPEC;
    hints.ai_socktype = SOCK_STREAM;

    if ((rv = getaddrinfo(host, port, &hints, &ai)) != 0) {
      fprintf(stderr, "[%d] failed to getaddrinfo to peer #%d\n", my_index, i);
      continue;
    }

    for (p = ai; p != NULL; p = p->ai_next) {
      if ((client_fd = socket(p->ai_family, p->ai_socktype, p->ai_protocol)) == -1) {
        continue;
      }

      if ((client = st_netfd_open(client_fd)) == NULL) {
        close(client_fd);
        continue;
      }

      if ((rv = st_connect(client, p->ai_addr, p->ai_addrlen, ST_UTIME_NO_TIMEOUT)) != 0) {
        st_netfd_close(client);
        close(client_fd);
        continue;
      } else {
        fd_list[i] = client;
      }

      // 写入 1 字节的 rpc 握手头
      if ((rv = st_write(client, (char *)&my_index, 1, ST_UTIME_NO_TIMEOUT)) == -1) {
        fprintf(stderr, "[%d] handshake failed.\n", my_index);
      }

      fd_list[i] = client;
      break;
    }

    if (p == NULL) {
      fprintf(stderr, "[%d] failed to connect to peer #%d.\n", my_index, i);
    }

    freeaddrinfo(ai);
    ai = NULL;
    p = NULL;

    // 模拟:发出第一个 rpc 包
    char message[] = "hello rpc.";
    rpcpkg_len len = strlen(message);
    rpcpkg_len nlen = HTON(len); // network order of len

    char *package = (char*)calloc(sizeof(rpcpkg_len) + len, sizeof(char));
    memcpy(package, &nlen, sizeof(len));
    memcpy(package + sizeof(len), message, len);

    fprintf(stdout, "[%d] construction an package: << ", my_index);
    for (int j=0; j<len + sizeof(len); j++) {
      fprintf(stdout, "%02X ", *((uint8_t*)package + j));
    }
    fprintf(stdout, " >>\n");

    if ((rv = st_write(client, package, len + sizeof(rpcpkg_len), ST_UTIME_NO_TIMEOUT)) == -1) {
      fprintf(stderr, "[%d] failed to write package into client\n", my_index);
    }

    free(package);
  }

  return NULL;

}
示例#27
0
hoxResult
hoxDbClient::WWW_authenticate( const std::string& sPlayerId,
                               const std::string& sHPassword )
{
    const char* FNAME = "hoxDbClient::WWW_authenticate";
    hoxResult result = hoxRC_ERR;

    hoxLog(LOG_DEBUG, "%s: ENTER. pid = [%s].", FNAME, sPlayerId.c_str());

    /* Open the socket connect to the server. */

    const char* szHost = WWW_HOST;
    const int   nPort  = WWW_PORT;
    st_netfd_t  nfd    = NULL;

    nfd = _open_client_socket( szHost, nPort );
    if ( nfd == NULL )
    {
        hoxLog(LOG_ERROR, "%s: Failed to open a client socket to [%s:%d].", FNAME, szHost, nPort);
        return hoxRC_ERR;
    }

    /* Send the request. */

    std::string sRequest;

    sRequest = std::string("GET /blog/hoxchess-login.php")
                + "?pid="      + sPlayerId 
                + "&password="******" HTTP/1.0\r\n"
             + "Host: " + szHost + "\r\n"
             + "Content-Length: 0\r\n"
             + "\r\n";

    const int nToSend = sRequest.size();
    ssize_t   nSent = 0;

    hoxLog(LOG_DEBUG, "%s: Sending (%d bytes): [\n%s]...", FNAME, sRequest.size(), sRequest.c_str());
    nSent = st_write( nfd, 
                      sRequest.c_str(), 
                      nToSend, 
                      ST_UTIME_NO_TIMEOUT );
    if ( nSent < nToSend )
    {
        hoxLog(LOG_SYS_WARN, "%s: Failed to write to socket", FNAME);
        st_netfd_close( nfd );
        return hoxRC_OK;
    }

    /* Read the response back. */

    hoxLog(LOG_DEBUG, "%s: Reading response...", FNAME);
    std::string sResponse;
    ssize_t     nRead = 0;
    const int   MAX_TO_READ = 512;  // *** Hard-coded max-buffer-size.
    char        szBuffer[MAX_TO_READ];

    for (;;)
    {
        memset( szBuffer, 0, MAX_TO_READ );  // zero-out.
        nRead = st_read( nfd, szBuffer, MAX_TO_READ, ST_UTIME_NO_TIMEOUT );
        if ( nRead > 0 )
        {
            sResponse.append( szBuffer, nRead ); 
        }
        else if ( nRead != MAX_TO_READ )  // Connection closed?
        {
            break; // Done
        }
    }

    hoxLog(LOG_DEBUG, "%s: Received (%d bytes): [\n%s].", FNAME, sResponse.size(), sResponse.c_str());

    /* Check for return-code. */

    std::string::size_type npBody = sResponse.find("\r\n\r\n");

    if (   npBody != std::string::npos
        && sResponse.substr(npBody+4).find_first_of('0') == 0 )
    {
        result = hoxRC_OK;
    }

    /* Cleanup and return. */

    st_netfd_close( nfd );
    return result;
}
示例#28
0
void *
handle_connection(void *fd2)
{
    int rc, n, len;
    int ffd;
    char *buf, *fn;
    int i;

    st_netfd_t fd = (st_netfd_t)fd2;

    buf = malloc(4096);
    rc = 0;

 again:
    rc += st_read(fd, buf + rc, 4096 - rc,-1);
    if(rc < 0) { perror("st_read"); goto fail; }

    if(rc < 4)
        goto fail;

    if(memcmp(buf, "GET ", 4) != 0)
        goto fail;

    for(i = 5; i < rc; i++)
        if(buf[i] == ' ' || buf[i] == '\r' || buf[i] == '\n')
            break;
    if(i == rc && rc < 4096)
        goto again;

    len = strlen(root);

    fn = malloc(len + 1 + i - 5 + 12);
    strcpy(fn, root);
    memcpy(fn + len, buf + 5, i - 5);

    if(buf[i - 1] == '/')
        strcpy(fn + len + i - 5, "index.html");
    else
        fn[len + i - 5] = '\0';

    i--;

 search:
    while(i < rc - 3)
      if(buf[i++] == '\r' && buf[i] == '\n'){
        i++; if(buf[i++] == '\r' && buf[i] == '\n')
          goto send;
      }

    if(rc < 4096) {
        rc += st_read(fd, buf + rc, 4096 - rc,-1);
        goto search;
    }

 send:
#ifdef STATIC
    rc = st_write(fd, &resp, resp_size, 60000000);
    if(rc != resp_size) { perror("st_write"); goto fail; }
#else
    ffd = open(fn, O_RDONLY,0);
    if(ffd < 0) {
        int err;
        char *message;
        if(errno == ENOENT) {
            err = 404;
            message = "File doesn't exist";
        } else if(errno == EACCES || errno == EPERM) {
            err = 403;
            message = "Forbidden";
        } else if(errno == EMFILE || errno == ENFILE) {
            err = 500;
            message = "Out of file descriptors";
        } else if(errno == ENOMEM) {
            err = 500;
            message = "Out of memory";
        } else {
            err = 500;
            message = "Unknown error";
        }
        n = snprintf(buf, 4096,
                     "HTTP/1.1 %d %s\r\n"
                     "Content-Type: text/html\r\n"
                     "Server: Trivial-st\r\n"
                     "Connection: close\r\n"
                     "\r\n"
                     "<html><body><p>Couldn't open %s: %s</body></html>\r\n",
                     err, message, fn, message);
        free(fn);
    } else {
        free(fn);
        n = snprintf(buf, 4096,
                     "HTTP/1.1 200 OK\r\n"
                     "Content-Type: text/html\r\n"
                     "Server: Trivial-st\r\n"
                     "Connection: close\r\n"
                     "\r\n");
        rc = read(ffd, buf + n, 4096 - n);
        if(rc >= 0)
            n += rc;
    }

    rc = st_write(fd, buf, n,-1);
    if(rc < 0) { perror("write"); if(ffd >= 0) close(ffd); goto fail; }

    if(ffd >= 0) {
        while(1) {
            n = read(ffd, buf, 4096);
            if(n <= 0) break;
            rc = st_write(fd, buf, 4096,-1);
            st_sleep(0);
        }
    }

    close(ffd);
#endif

 fail:
    st_netfd_close(fd);
    free(buf);
    st_thread_exit(NULL);
}
示例#29
0
ssize_t st_writev(_st_netfd_t *fd, const struct iovec *iov, int iov_size,
		  st_utime_t timeout)
{
  ssize_t n, rv;
  size_t nleft, nbyte;
  int index, iov_cnt;
  struct iovec *tmp_iov;
  struct iovec local_iov[_LOCAL_MAXIOV];

  /* Calculate the total number of bytes to be sent */
  nbyte = 0;
  for (index = 0; index < iov_size; index++)
    nbyte += iov[index].iov_len;

  rv = (ssize_t)nbyte;
  nleft = nbyte;
  tmp_iov = (struct iovec *) iov;	/* we promise not to modify iov */
  iov_cnt = iov_size;

  while (nleft > 0) {
    if (iov_cnt == 1) {
      if (st_write(fd, tmp_iov[0].iov_base, nleft, timeout) != (ssize_t) nleft)
	rv = -1;
      break;
    }
    if ((n = writev(fd->osfd, tmp_iov, iov_cnt)) < 0) {
      if (errno == EINTR)
	continue;
      if (!_IO_NOT_READY_ERROR) {
	rv = -1;
	break;
      }
    } else {
      if ((size_t) n == nleft)
	break;
      nleft -= n;
      /* Find the next unwritten vector */
      n = (ssize_t)(nbyte - nleft);
      for (index = 0; (size_t) n >= iov[index].iov_len; index++)
	n -= iov[index].iov_len;

      if (tmp_iov == iov) {
	/* Must copy iov's around */
	if (iov_size - index <= _LOCAL_MAXIOV) {
	  tmp_iov = local_iov;
	} else {
	  tmp_iov = calloc(1, (iov_size - index) * sizeof(struct iovec));
	  if (tmp_iov == NULL)
	    return -1;
	}
      }

      /* Fill in the first partial read */
      tmp_iov[0].iov_base = &(((char *)iov[index].iov_base)[n]);
      tmp_iov[0].iov_len = iov[index].iov_len - n;
      index++;
      /* Copy the remaining vectors */
      for (iov_cnt = 1; index < iov_size; iov_cnt++, index++) {
	tmp_iov[iov_cnt].iov_base = iov[index].iov_base;
	tmp_iov[iov_cnt].iov_len = iov[index].iov_len;
      }
    }
    /* Wait until the socket becomes writable */
    if (st_netfd_poll(fd, POLLOUT, timeout) < 0) {
      rv = -1;
      break;
    }
  }

  if (tmp_iov != iov && tmp_iov != local_iov)
    free(tmp_iov);

  return rv;
}
示例#30
0
void *handle_connection(void *arg) {
  st_netfd_t client_nfd = (st_netfd_t)arg;
  struct http_stream *s = http_stream_create(HTTP_SERVER, SEC2USEC(5));
  char buf[4*1024];
  int error = 0;
  struct http_stream *cs = NULL;
  uri_t *u = uri_new();
  int should_close = 1;
  for (;;) {
    should_close = 1;
    if (s->status != HTTP_STREAM_OK) break;
    cs = NULL;
    error = 0;
    s->timeout = SEC2USEC(5);
    int status = http_stream_request_read(s, client_nfd);
    s->timeout = SEC2USEC(30); // longer timeout for the rest
    if (status != HTTP_STREAM_OK) {
      if (s->status == HTTP_STREAM_CLOSED || s->status == HTTP_STREAM_TIMEOUT) {
        error = 1;
      } else {
        error = 400;
      }
      goto release;
    }
    cs = http_stream_create(HTTP_CLIENT, SEC2USEC(30));
    //http_request_debug_print(s->req);

    fprintf(stderr, "request uri: %s\n", s->req->uri);
    const char *error_at = NULL;
    uri_clear(u);
    if (uri_parse(u, s->req->uri, strlen(s->req->uri), &error_at) == 0) {
      fprintf(stderr, "uri_parse error: %s\n", error_at);
      error = 400;
      goto release;
    }
    uri_normalize(u);
    if (http_stream_connect(cs, u->host, u->port) != HTTP_STREAM_OK) { error = 504; goto release; }
    http_request_header_remove(s->req, "Accept-Encoding");
    http_request_header_remove(s->req, "Proxy-Connection");
    /* TODO: need to expose a copy api for http message */
    http_request_t *tmp_req = cs->req;
    cs->req = s->req;
    char *request_uri = uri_compose_partial(u);
    char *tmp_uri = s->req->uri;
    cs->req->uri = request_uri;
    if (http_stream_request_send(cs) != HTTP_STREAM_OK) { error = 504; goto release; }
    cs->req = tmp_req;
    s->req->uri = tmp_uri;
    free(request_uri);

    /* TODO: fix this. post might not contain data. probably move this logic into stream */
    size_t total = 0;
    if (g_strcmp0("POST", s->req->method) == 0) {
      for (;;) {
        ssize_t nr = sizeof(buf);
        status = http_stream_read(s, buf, &nr);
        fprintf(stderr, "server http_stream_read nr: %zd\n", nr);
        if (nr < 0 || status != HTTP_STREAM_OK) { error = 1; goto release; }
        if (nr == 0) break;
        /*fwrite(buf, sizeof(char), nr, stdout);*/
        ssize_t nw = st_write(cs->nfd, buf, nr, s->timeout);
        if (nw != nr) { error=1; goto release; }
        fprintf(stderr, "st_write nw: %zd\n", nr);
        total += nr;
      }
      fprintf(stderr, "http_stream_read total: %zu\n", total);
    }

    if (http_stream_response_read(cs) != HTTP_STREAM_OK) { error = 502; goto release; }

    /* TODO: properly create a new response and copy headers */
    http_response_t *tmp_resp = s->resp;
    s->resp = cs->resp;
    s->resp->http_version = "HTTP/1.1";
    http_response_header_remove(s->resp, "Content-Length");
    http_response_header_remove(s->resp, "Transfer-Encoding");
    if (s->resp->status_code != 204)
        http_response_header_append(s->resp, "Transfer-Encoding", "chunked");
    ssize_t nw = http_stream_response_send(s, 0);
    s->resp = tmp_resp;

    fprintf(stderr, "http_stream_response_send: %zd\n", nw);
    if (s->resp->status_code != 204 &&
           (cs->content_size > 0 || cs->transfer_encoding == TE_CHUNKED)) {
      total = 0;
      fprintf(stderr, "content size: %zd\n", cs->content_size);
      for (;;) {
        ssize_t nr = sizeof(buf);
        status = http_stream_read(cs, buf, &nr);
        fprintf(stderr, "client http_stream_read nr: %zd\n", nr);
        if (nr <= 0 || status != HTTP_STREAM_OK) break;
        /*fwrite(buf, sizeof(char), nr, stdout);*/
        total += nr;
        if (http_stream_send_chunk(s, buf, nr) != HTTP_STREAM_OK) break;
      }
      fprintf(stderr, "written to client: %zu\n", total);
      if (total > 0 && s->status == HTTP_STREAM_OK) {
        http_stream_send_chunk_end(s);
      } else {
        fprintf(stderr, "for request: %s status: %d\n", s->req->uri, s->status);
      }
    }
release:
    if (!error) {
        if ((g_strcmp0("HTTP/1.1", s->req->http_version) == 0) &&
          (g_strcmp0(http_request_header_getstr(s->req, "Connection"), "close") != 0)) {
          // if HTTP/1.1 client and no Connection: close, then don't close
          should_close = 0;
        } else if (g_strcmp0(http_request_header_getstr(s->req, "Connection"), "keepalive") == 0) {
          should_close = 0;
        }
    }
    http_request_clear(s->req);
    uri_clear(u);
    if (cs) http_stream_close(cs);
    /* TODO: break loop if HTTP/1.0 and not keep-alive */
    if (error) {
      fprintf(stderr, "ERROR: %d STATUS: %d, exiting\n", error, s->status);
      /* TODO: use reason string */
      if (error >= 400 && s->status != HTTP_STREAM_CLOSED) {
        http_response_free(s->resp);
        s->resp = http_response_new(error, "Error");
        http_response_header_append(s->resp, "Content-Length", "0");
        s->status = HTTP_STREAM_OK; /* TODO: might want to move this logic into http_stream */
        http_stream_response_send(s, 0);
      }
      break;
    }
    if (should_close) break;
  }
  fprintf(stderr, "exiting handle_connection (should_close: %u)\n", should_close);
  uri_free(u);
  http_stream_close(s);
  return NULL;
}