<commit_before>/////////////////////////////////////////////////////////////////////////
// $Id: eth_linux.cc,v 1.4 2001/10/03 14:53:22 fries Exp $
/////////////////////////////////////////////////////////////////////////
//
//  Copyright (C) 2001  MandrakeSoft S.A.
//
//    MandrakeSoft S.A.
//    43, rue d'Aboukir
//    75002 Paris - France
//    http://www.linux-mandrake.com/
//    http://www.mandrakesoft.com/
//
//  This library is free software; you can redistribute it and/or
//  modify it under the terms of the GNU Lesser General Public
//  License as published by the Free Software Foundation; either
//  version 2 of the License, or (at your option) any later version.
//
//  This library is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
//  Lesser General Public License for more details.
//
//  You should have received a copy of the GNU Lesser General Public
//  License along with this library; if not, write to the Free Software
//  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA

// Peter Grehan (grehan@iprg.nokia.com) coded all of this
// NE2000/ether stuff.

// eth_linux.cc - A Linux socket filter adaptation of the FreeBSD BPF driver
// <splite@purdue.edu> 21 June 2001
//
// Problems and limitations:
//   - packets cannot be sent from BOCHS to the host
//   - Linux kernel sometimes gets network watchdog timeouts under emulation
//   - author doesn't know C++
//
//   The config line in .bochsrc should look something like:
//
//  ne2k: ioaddr=0x280, irq=10, mac=00:a:b:c:1:2, ethmod=linux, ethdev=eth0
//

#include "bochs.h"
#ifdef ETH_LINUX
#define LOG_THIS this->

extern "C" {
#include <errno.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <netpacket/packet.h>
#include <netinet/in.h>
#include <net/ethernet.h>
#include <net/if.h>
#include <linux/types.h>
#include <linux/filter.h>
};

#define BX_PACKET_POLL  1000    // Poll for a frame every 1000 usecs

#define BX_PACKET_BUFSIZ 2048	// Enough for an ether frame

// template filter for a unicast mac address and all
// multicast/broadcast frames
static const struct sock_filter macfilter[] = {
  BPF_STMT(BPF_LD|BPF_W|BPF_ABS, 2),
  BPF_JUMP(BPF_JMP|BPF_JEQ|BPF_K, 0xaaaaaaaa, 0, 2),
  BPF_STMT(BPF_LD|BPF_H|BPF_ABS, 0),
  BPF_JUMP(BPF_JMP|BPF_JEQ|BPF_K, 0x0000aaaa, 2, 0),
  BPF_STMT(BPF_LD|BPF_B|BPF_ABS, 0),
  BPF_JUMP(BPF_JMP|BPF_JSET|BPF_K, 0x01, 0, 1),
  BPF_STMT(BPF_RET, 1514),
  BPF_STMT(BPF_RET, 0),
};
#define BX_LSF_ICNT 8    // number of lsf instructions in macfilter

#if 0
// template filter for all frames
static const struct sock_filter promiscfilter[] = {
  BPF_STMT(BPF_RET, 1514)
};
#endif

//
//  Define the class. This is private to this module
//
class bx_linux_pktmover_c : public eth_pktmover_c {
public:
  bx_linux_pktmover_c(const char *netif,
		     const char *macaddr,
		     eth_rx_handler_t rxh,
		     void *rxarg);
  void sendpkt(void *buf, unsigned io_len);

private:
  unsigned char *linux_macaddr[6];
  int fd;
  int ifindex;
  static void rx_timer_handler(void *);
  void rx_timer(void);
  int rx_timer_index;
  struct sock_filter filter[BX_LSF_ICNT];
};

//
//  Define the static class that registers the derived pktmover class,
// and allocates one on request.
//
class bx_linux_locator_c : public eth_locator_c {
public:
  bx_linux_locator_c(void) : eth_locator_c("linux") {}
protected:
  eth_pktmover_c *allocate(const char *netif,
			   const char *macaddr,
			   eth_rx_handler_t rxh,
			   void *rxarg) {
    return (new bx_linux_pktmover_c(netif, macaddr, rxh, rxarg));
  }
} bx_linux_match;

//
// Define the methods for the bx_linux_pktmover derived class
//

// the constructor
//
bx_linux_pktmover_c::bx_linux_pktmover_c(const char *netif,
				       const char *macaddr,
				       eth_rx_handler_t rxh,
				       void *rxarg)
{
  struct sockaddr_ll sll;
  struct packet_mreq mr;
  struct ifreq ifr;
  struct sock_fprog fp;

  memcpy(linux_macaddr, macaddr, 6);

  // Open packet socket
  //
  if ((this->fd = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL))) == -1) {
    if (errno == EACCES)
      BX_PANIC(("eth_linux: must be root or have CAP_NET_RAW capability to open socket"));
    else
      BX_PANIC(("eth_linux: could not open socket"));
    this->fd = -1;
    return;
  }

  // Translate interface name to index
  //
  memset(&ifr, 0, sizeof(ifr));
  strcpy(ifr.ifr_name, netif);
  if (ioctl(this->fd, SIOCGIFINDEX, &ifr) == -1) {
    BX_PANIC(("eth_linux: could not get index for interface %s\n", netif));
    close(fd);
    this->fd = -1;
    return;
  }
  this->ifindex = ifr.ifr_ifindex;

  // Bind to given interface
  //
  memset(&sll, 0, sizeof(sll));
  sll.sll_family = AF_PACKET;
  sll.sll_ifindex = this->ifindex;
  if (bind(fd, (struct sockaddr *)&sll, (socklen_t)sizeof(sll)) == -1) {
    BX_PANIC(("eth_linux: could not bind to interface %s\n", netif));
    close(fd);
    this->fd = -1;
    return;
  }

  // Put the device into promisc mode.
  //
  memset(&mr, 0, sizeof(mr));
  mr.mr_ifindex = this->ifindex;
  mr.mr_type = PACKET_MR_PROMISC;
  if (setsockopt(this->fd, SOL_PACKET, PACKET_ADD_MEMBERSHIP, (void *)&mr, (socklen_t)sizeof(mr)) == -1) {
    BX_PANIC(("eth_linux: could not enable promisc mode: %s\n", strerror(errno)));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Set up non-blocking i/o
  if (fcntl(this->fd, F_SETFL, O_NONBLOCK) == -1) {
    BX_PANIC(("eth_linux: could not set non-blocking i/o on socket"));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Install a filter
#ifdef notdef
  memcpy(&this->filter, promiscfilter, sizeof(promiscfilter));
  fp.len   = 1;
#endif
  memcpy(&this->filter, macfilter, sizeof(macfilter));
  this->filter[1].k = (macaddr[2] & 0xff) << 24 | (macaddr[3] & 0xff) << 16 |
    (macaddr[4] & 0xff) << 8  | (macaddr[5] & 0xff);
  this->filter[3].k = (macaddr[0] & 0xff) << 8 | (macaddr[1] & 0xff);
  fp.len = BX_LSF_ICNT;
  fp.filter = this->filter;
  BX_INFO(("eth_linux: fp.len=%d fp.filter=%lx", fp.len, fp.filter));
  if (setsockopt(this->fd, SOL_SOCKET, SO_ATTACH_FILTER, &fp, sizeof(fp)) < 0) {
    BX_PANIC(("eth_linux: could not set socket filter: %s", strerror(errno)));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Start the rx poll
  this->rx_timer_index =
    bx_pc_system.register_timer(this, this->rx_timer_handler, BX_PACKET_POLL,
				1, 1); // continuous, active

  this->rxh   = rxh;
  this->rxarg = rxarg;
  BX_INFO(("eth_linux: enabled NE2K emulation on interface %s\n", netif));
}

// the output routine - called with pre-formatted ethernet frame.
void
bx_linux_pktmover_c::sendpkt(void *buf, unsigned io_len)
{
  int status;

  if (this->fd != -1)
    status = write(this->fd, buf, io_len);
  if (status == -1)
    BX_INFO(("eth_linux: write failed: %s", strerror(errno)));
}

// The receive poll process
void
bx_linux_pktmover_c::rx_timer_handler(void *this_ptr)
{
  bx_linux_pktmover_c *class_ptr = (bx_linux_pktmover_c *) this_ptr;

  class_ptr->rx_timer();
}

void
bx_linux_pktmover_c::rx_timer(void)
{
  int nbytes = 0;
  Bit8u rxbuf[BX_PACKET_BUFSIZ];
  struct sockaddr_ll sll;
  socklen_t fromlen;
  static unsigned char bcast_addr[6] = {0xff,0xff,0xff,0xff,0xff,0xff};

  if (this->fd == -1)
    return;

  fromlen = sizeof(sll);
  nbytes = recvfrom(this->fd, rxbuf, sizeof(rxbuf), 0, (struct sockaddr *)&sll, &fromlen);

  if (nbytes == -1) {
    if (errno != EAGAIN)
      BX_INFO(("eth_linux: error receiving packet: %s\n", strerror(errno)));
    return;
  }

  // this should be done with LSF someday
  // filter out packets sourced by us
  if (memcmp(sll.sll_addr, this->linux_macaddr, 6) == 0)
    return;
  // let through broadcast, multicast, and our mac address
//  if ((memcmp(rxbuf, bcast_addr, 6) == 0) || (memcmp(rxbuf, this->linux_macaddr, 6) == 0) || rxbuf[0] & 0x01) {
    BX_DEBUG(("eth_linux: got packet: %d bytes, dst=%x:%x:%x:%x:%x:%x, src=%x:%x:%x:%x:%x:%x\n", nbytes, rxbuf[0], rxbuf[1], rxbuf[2], rxbuf[3], rxbuf[4], rxbuf[5], rxbuf[6], rxbuf[7], rxbuf[8], rxbuf[9], rxbuf[10], rxbuf[11]));
    (*rxh)(rxarg, rxbuf, nbytes);
//  }
}
#endif
<commit_msg>- add strerror(errno) on some log messages<commit_after>/////////////////////////////////////////////////////////////////////////
// $Id: eth_linux.cc,v 1.5 2001/10/06 17:30:19 bdenney Exp $
/////////////////////////////////////////////////////////////////////////
//
//  Copyright (C) 2001  MandrakeSoft S.A.
//
//    MandrakeSoft S.A.
//    43, rue d'Aboukir
//    75002 Paris - France
//    http://www.linux-mandrake.com/
//    http://www.mandrakesoft.com/
//
//  This library is free software; you can redistribute it and/or
//  modify it under the terms of the GNU Lesser General Public
//  License as published by the Free Software Foundation; either
//  version 2 of the License, or (at your option) any later version.
//
//  This library is distributed in the hope that it will be useful,
//  but WITHOUT ANY WARRANTY; without even the implied warranty of
//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
//  Lesser General Public License for more details.
//
//  You should have received a copy of the GNU Lesser General Public
//  License along with this library; if not, write to the Free Software
//  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA

// Peter Grehan (grehan@iprg.nokia.com) coded all of this
// NE2000/ether stuff.

// eth_linux.cc - A Linux socket filter adaptation of the FreeBSD BPF driver
// <splite@purdue.edu> 21 June 2001
//
// Problems and limitations:
//   - packets cannot be sent from BOCHS to the host
//   - Linux kernel sometimes gets network watchdog timeouts under emulation
//   - author doesn't know C++
//
//   The config line in .bochsrc should look something like:
//
//  ne2k: ioaddr=0x280, irq=10, mac=00:a:b:c:1:2, ethmod=linux, ethdev=eth0
//

#include "bochs.h"
#ifdef ETH_LINUX
#define LOG_THIS this->

extern "C" {
#include <errno.h>
#include <fcntl.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <sys/ioctl.h>
#include <netpacket/packet.h>
#include <netinet/in.h>
#include <net/ethernet.h>
#include <net/if.h>
#include <linux/types.h>
#include <linux/filter.h>
};

#define BX_PACKET_POLL  1000    // Poll for a frame every 1000 usecs

#define BX_PACKET_BUFSIZ 2048	// Enough for an ether frame

// template filter for a unicast mac address and all
// multicast/broadcast frames
static const struct sock_filter macfilter[] = {
  BPF_STMT(BPF_LD|BPF_W|BPF_ABS, 2),
  BPF_JUMP(BPF_JMP|BPF_JEQ|BPF_K, 0xaaaaaaaa, 0, 2),
  BPF_STMT(BPF_LD|BPF_H|BPF_ABS, 0),
  BPF_JUMP(BPF_JMP|BPF_JEQ|BPF_K, 0x0000aaaa, 2, 0),
  BPF_STMT(BPF_LD|BPF_B|BPF_ABS, 0),
  BPF_JUMP(BPF_JMP|BPF_JSET|BPF_K, 0x01, 0, 1),
  BPF_STMT(BPF_RET, 1514),
  BPF_STMT(BPF_RET, 0),
};
#define BX_LSF_ICNT 8    // number of lsf instructions in macfilter

#if 0
// template filter for all frames
static const struct sock_filter promiscfilter[] = {
  BPF_STMT(BPF_RET, 1514)
};
#endif

//
//  Define the class. This is private to this module
//
class bx_linux_pktmover_c : public eth_pktmover_c {
public:
  bx_linux_pktmover_c(const char *netif,
		     const char *macaddr,
		     eth_rx_handler_t rxh,
		     void *rxarg);
  void sendpkt(void *buf, unsigned io_len);

private:
  unsigned char *linux_macaddr[6];
  int fd;
  int ifindex;
  static void rx_timer_handler(void *);
  void rx_timer(void);
  int rx_timer_index;
  struct sock_filter filter[BX_LSF_ICNT];
};

//
//  Define the static class that registers the derived pktmover class,
// and allocates one on request.
//
class bx_linux_locator_c : public eth_locator_c {
public:
  bx_linux_locator_c(void) : eth_locator_c("linux") {}
protected:
  eth_pktmover_c *allocate(const char *netif,
			   const char *macaddr,
			   eth_rx_handler_t rxh,
			   void *rxarg) {
    return (new bx_linux_pktmover_c(netif, macaddr, rxh, rxarg));
  }
} bx_linux_match;

//
// Define the methods for the bx_linux_pktmover derived class
//

// the constructor
//
bx_linux_pktmover_c::bx_linux_pktmover_c(const char *netif,
				       const char *macaddr,
				       eth_rx_handler_t rxh,
				       void *rxarg)
{
  struct sockaddr_ll sll;
  struct packet_mreq mr;
  struct ifreq ifr;
  struct sock_fprog fp;

  memcpy(linux_macaddr, macaddr, 6);

  // Open packet socket
  //
  if ((this->fd = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_ALL))) == -1) {
    if (errno == EACCES)
      BX_PANIC(("eth_linux: must be root or have CAP_NET_RAW capability to open socket"));
    else
      BX_PANIC(("eth_linux: could not open socket: %s", strerror(errno)));
    this->fd = -1;
    return;
  }

  // Translate interface name to index
  //
  memset(&ifr, 0, sizeof(ifr));
  strcpy(ifr.ifr_name, netif);
  if (ioctl(this->fd, SIOCGIFINDEX, &ifr) == -1) {
    BX_PANIC(("eth_linux: could not get index for interface '%s'\n", netif));
    close(fd);
    this->fd = -1;
    return;
  }
  this->ifindex = ifr.ifr_ifindex;

  // Bind to given interface
  //
  memset(&sll, 0, sizeof(sll));
  sll.sll_family = AF_PACKET;
  sll.sll_ifindex = this->ifindex;
  if (bind(fd, (struct sockaddr *)&sll, (socklen_t)sizeof(sll)) == -1) {
    BX_PANIC(("eth_linux: could not bind to interface '%s': %s\n", netif, strerror(errno)));
    close(fd);
    this->fd = -1;
    return;
  }

  // Put the device into promisc mode.
  //
  memset(&mr, 0, sizeof(mr));
  mr.mr_ifindex = this->ifindex;
  mr.mr_type = PACKET_MR_PROMISC;
  if (setsockopt(this->fd, SOL_PACKET, PACKET_ADD_MEMBERSHIP, (void *)&mr, (socklen_t)sizeof(mr)) == -1) {
    BX_PANIC(("eth_linux: could not enable promisc mode: %s\n", strerror(errno)));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Set up non-blocking i/o
  if (fcntl(this->fd, F_SETFL, O_NONBLOCK) == -1) {
    BX_PANIC(("eth_linux: could not set non-blocking i/o on socket"));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Install a filter
#ifdef notdef
  memcpy(&this->filter, promiscfilter, sizeof(promiscfilter));
  fp.len   = 1;
#endif
  memcpy(&this->filter, macfilter, sizeof(macfilter));
  this->filter[1].k = (macaddr[2] & 0xff) << 24 | (macaddr[3] & 0xff) << 16 |
    (macaddr[4] & 0xff) << 8  | (macaddr[5] & 0xff);
  this->filter[3].k = (macaddr[0] & 0xff) << 8 | (macaddr[1] & 0xff);
  fp.len = BX_LSF_ICNT;
  fp.filter = this->filter;
  BX_INFO(("eth_linux: fp.len=%d fp.filter=%lx", fp.len, fp.filter));
  if (setsockopt(this->fd, SOL_SOCKET, SO_ATTACH_FILTER, &fp, sizeof(fp)) < 0) {
    BX_PANIC(("eth_linux: could not set socket filter: %s", strerror(errno)));
    close(this->fd);
    this->fd = -1;
    return;
  }

  // Start the rx poll
  this->rx_timer_index =
    bx_pc_system.register_timer(this, this->rx_timer_handler, BX_PACKET_POLL,
				1, 1); // continuous, active

  this->rxh   = rxh;
  this->rxarg = rxarg;
  BX_INFO(("eth_linux: enabled NE2K emulation on interface %s\n", netif));
}

// the output routine - called with pre-formatted ethernet frame.
void
bx_linux_pktmover_c::sendpkt(void *buf, unsigned io_len)
{
  int status;

  if (this->fd != -1)
    status = write(this->fd, buf, io_len);
  if (status == -1)
    BX_INFO(("eth_linux: write failed: %s", strerror(errno)));
}

// The receive poll process
void
bx_linux_pktmover_c::rx_timer_handler(void *this_ptr)
{
  bx_linux_pktmover_c *class_ptr = (bx_linux_pktmover_c *) this_ptr;

  class_ptr->rx_timer();
}

void
bx_linux_pktmover_c::rx_timer(void)
{
  int nbytes = 0;
  Bit8u rxbuf[BX_PACKET_BUFSIZ];
  struct sockaddr_ll sll;
  socklen_t fromlen;
  static unsigned char bcast_addr[6] = {0xff,0xff,0xff,0xff,0xff,0xff};

  if (this->fd == -1)
    return;

  fromlen = sizeof(sll);
  nbytes = recvfrom(this->fd, rxbuf, sizeof(rxbuf), 0, (struct sockaddr *)&sll, &fromlen);

  if (nbytes == -1) {
    if (errno != EAGAIN)
      BX_INFO(("eth_linux: error receiving packet: %s\n", strerror(errno)));
    return;
  }

  // this should be done with LSF someday
  // filter out packets sourced by us
  if (memcmp(sll.sll_addr, this->linux_macaddr, 6) == 0)
    return;
  // let through broadcast, multicast, and our mac address
//  if ((memcmp(rxbuf, bcast_addr, 6) == 0) || (memcmp(rxbuf, this->linux_macaddr, 6) == 0) || rxbuf[0] & 0x01) {
    BX_DEBUG(("eth_linux: got packet: %d bytes, dst=%x:%x:%x:%x:%x:%x, src=%x:%x:%x:%x:%x:%x\n", nbytes, rxbuf[0], rxbuf[1], rxbuf[2], rxbuf[3], rxbuf[4], rxbuf[5], rxbuf[6], rxbuf[7], rxbuf[8], rxbuf[9], rxbuf[10], rxbuf[11]));
    (*rxh)(rxarg, rxbuf, nbytes);
//  }
}
#endif
<|endoftext|>


<commit_before>#include "udt_socket.h"

#pragma warning(disable:4251)
#include "udt.h"
#pragma warning(default:4251)

UDTSocket::UDTSocket()
: m_udpSocket(INVALID_SOCKET)
{
	m_socket = UDT::socket(AF_INET, SOCK_STREAM, IPPROTO_UDP);
}

UDTSocket::UDTSocket(int socket, bool isUdp)
: m_udpSocket(INVALID_SOCKET)
{
	if(isUdp)
	{
		m_udpSocket = socket;
		m_socket = UDT::socket(AF_INET, SOCK_STREAM, IPPROTO_UDP);
	}
	else
	{
		m_socket = socket;
	}
}

UDTSocket::UDTSocket(int udpSocket, int socket)
: m_socket(socket)
, m_udpSocket(udpSocket)
{
}

UDTSocket::~UDTSocket()
{
}

bool UDTSocket::Bind(const std::string& host, int port)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	if(m_udpSocket == INVALID_SOCKET)
	{
		sockaddr_in si;
		if(host.empty())
		{
			si.sin_addr.s_addr = INADDR_ANY;
		}
		else
		{
			hostent* h = gethostbyname(host.c_str());
			if(h)
			{
				si.sin_addr.s_addr = *(u_long*)h->h_addr;
			}
			else
			{
				si.sin_addr.s_addr = inet_addr(host.c_str());
			}
		}

		si.sin_port = htons(port);
		si.sin_family = AF_INET;
		return UDT::bind(m_socket, (sockaddr*)&si, sizeof(si)) == 0;
	}
	else
	{
		int res = UDT::bind(m_socket, m_udpSocket);
		if (res == SOCKET_ERROR)
		{
			return false;
		}

		bool bVal = true;
		if(UDT::setsockopt(m_socket, 0, UDT_RENDEZVOUS, (void*)&bVal, sizeof(bool)) == SOCKET_ERROR)
		{
			return false;
		}

		return true;
	}
}

bool UDTSocket::Listen(int limit)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	return UDT::listen(m_socket, limit) == 0;
}

int UDTSocket::Accept(std::string& ip, int& port)
{
	if(m_socket == INVALID_SOCKET)
	{
		return 0;
	}

	sockaddr_in si;
	int len = sizeof(si);
	int sock = UDT::accept(m_socket, (sockaddr*)&si, &len);
	ip = inet_ntoa(si.sin_addr);
	port = si.sin_port;
	return sock;
}

bool UDTSocket::Connect(const std::string& host, int port)
{
	if(m_socket == INVALID_SOCKET || host.empty())
	{
		return false;
	}

	sockaddr_in si;
	hostent* h = gethostbyname(host.c_str());
	if(h)
	{
		si.sin_addr.s_addr = *(u_long*)h->h_addr;
	}
	else
	{
		si.sin_addr.s_addr = inet_addr(host.c_str());
	}

	si.sin_port = htons(port);
	si.sin_family = AF_INET;

	return UDT::connect(m_socket, (sockaddr*)&si, sizeof(si)) == 0;
}

bool UDTSocket::Send(char* data, int len)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	CSLocker locker(&m_cs);
	int sendlen = len;
	while (sendlen > 0)
	{
		int res = UDT::send(m_socket, data + len - sendlen, sendlen, 0);
		if(res <= 0)
		{
			return false;
		}

		sendlen -= res;
	}

	return true;
}

bool UDTSocket::Recv(char* data, int len)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	int recvlen = len;
	while (recvlen > 0)
	{
		int res = UDT::recv(m_socket, data + len - recvlen, recvlen, 0);
		if(res <= 0)
		{
			return false;
		}

		recvlen -= res;
	}

	return true;
}

bool UDTSocket::Close()
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	if(m_udpSocket != INVALID_SOCKET)
	{
		shutdown(m_udpSocket, SD_BOTH);
#ifdef WIN32
		closesocket(m_udpSocket);
#else
		close(m_udpSocket);
#endif/*WIN32*/
	}

	return UDT::close(m_socket) == 0;
}

void UDTSocket::GetIPPort(std::string& ip, int& port)
{
	sockaddr_in addr = {0};
#ifdef WIN32
		int len = sizeof(addr);
#else
		unsigned int len = sizeof(addr);
#endif/*WIN32*/
	if(m_socket != INVALID_SOCKET)
	{
		if ((m_udpSocket != INVALID_SOCKET && !getsockname(m_udpSocket, (sockaddr*)&addr, &len)) ||
			!UDT::getsockname(m_socket, (sockaddr*)&addr, (int*)&len))
		{
			ip = inet_ntoa(addr.sin_addr);
			port = ntohs(addr.sin_port);
		}
	}
}

int UDTSocket::GetSocket()
{
	return m_socket;
}<commit_msg>little fix<commit_after>#include "udt_socket.h"

#pragma warning(disable:4251)
#include "udt.h"
#pragma warning(default:4251)

UDTSocket::UDTSocket()
: m_udpSocket(INVALID_SOCKET)
{
	m_socket = UDT::socket(AF_INET, SOCK_STREAM, IPPROTO_UDP);
}

UDTSocket::UDTSocket(int socket, bool isUdp)
: m_udpSocket(INVALID_SOCKET)
{
	if(isUdp)
	{
		m_udpSocket = socket;
		m_socket = UDT::socket(AF_INET, SOCK_STREAM, IPPROTO_UDP);
	}
	else
	{
		m_socket = socket;
	}
}

UDTSocket::UDTSocket(int udpSocket, int socket)
: m_socket(socket)
, m_udpSocket(udpSocket)
{
}

UDTSocket::~UDTSocket()
{
	Close();
}

bool UDTSocket::Bind(const std::string& host, int port)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	if(m_udpSocket == INVALID_SOCKET)
	{
		sockaddr_in si;
		if(host.empty())
		{
			si.sin_addr.s_addr = INADDR_ANY;
		}
		else
		{
			hostent* h = gethostbyname(host.c_str());
			if(h)
			{
				si.sin_addr.s_addr = *(u_long*)h->h_addr;
			}
			else
			{
				si.sin_addr.s_addr = inet_addr(host.c_str());
			}
		}

		si.sin_port = htons(port);
		si.sin_family = AF_INET;
		return UDT::bind(m_socket, (sockaddr*)&si, sizeof(si)) == 0;
	}
	else
	{
		int res = UDT::bind(m_socket, m_udpSocket);
		if (res == SOCKET_ERROR)
		{
			return false;
		}

		bool bVal = true;
		if(UDT::setsockopt(m_socket, 0, UDT_RENDEZVOUS, (void*)&bVal, sizeof(bool)) == SOCKET_ERROR)
		{
			return false;
		}

		return true;
	}
}

bool UDTSocket::Listen(int limit)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	return UDT::listen(m_socket, limit) == 0;
}

int UDTSocket::Accept(std::string& ip, int& port)
{
	if(m_socket == INVALID_SOCKET)
	{
		return 0;
	}

	sockaddr_in si;
	int len = sizeof(si);
	int sock = UDT::accept(m_socket, (sockaddr*)&si, &len);
	ip = inet_ntoa(si.sin_addr);
	port = si.sin_port;
	return sock;
}

bool UDTSocket::Connect(const std::string& host, int port)
{
	if(m_socket == INVALID_SOCKET || host.empty())
	{
		return false;
	}

	sockaddr_in si;
	hostent* h = gethostbyname(host.c_str());
	if(h)
	{
		si.sin_addr.s_addr = *(u_long*)h->h_addr;
	}
	else
	{
		si.sin_addr.s_addr = inet_addr(host.c_str());
	}

	si.sin_port = htons(port);
	si.sin_family = AF_INET;

	return UDT::connect(m_socket, (sockaddr*)&si, sizeof(si)) == 0;
}

bool UDTSocket::Send(char* data, int len)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	CSLocker locker(&m_cs);
	int sendlen = len;
	while (sendlen > 0)
	{
		int res = UDT::send(m_socket, data + len - sendlen, sendlen, 0);
		if(res <= 0)
		{
			return false;
		}

		sendlen -= res;
	}

	return true;
}

bool UDTSocket::Recv(char* data, int len)
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	int recvlen = len;
	while (recvlen > 0)
	{
		int res = UDT::recv(m_socket, data + len - recvlen, recvlen, 0);
		if(res <= 0)
		{
			return false;
		}

		recvlen -= res;
	}

	return true;
}

bool UDTSocket::Close()
{
	if(m_socket == INVALID_SOCKET)
	{
		return false;
	}

	if(m_udpSocket != INVALID_SOCKET)
	{
		shutdown(m_udpSocket, SD_BOTH);
#ifdef WIN32
		closesocket(m_udpSocket);
#else
		close(m_udpSocket);
#endif/*WIN32*/
	}

	return UDT::close(m_socket) == 0;
}

void UDTSocket::GetIPPort(std::string& ip, int& port)
{
	sockaddr_in addr = {0};
#ifdef WIN32
		int len = sizeof(addr);
#else
		unsigned int len = sizeof(addr);
#endif/*WIN32*/
	if(m_socket != INVALID_SOCKET)
	{
		if ((m_udpSocket != INVALID_SOCKET && !getsockname(m_udpSocket, (sockaddr*)&addr, &len)) ||
			!UDT::getsockname(m_socket, (sockaddr*)&addr, (int*)&len))
		{
			ip = inet_ntoa(addr.sin_addr);
			port = ntohs(addr.sin_port);
		}
	}
}

int UDTSocket::GetSocket()
{
	return m_socket;
}<|endoftext|>


<commit_before>#include "game/car_tracker.h"
#include "gflags/gflags.h"

DECLARE_string(race_id);

namespace game {

namespace {
template <typename T> int sgn(T val) {
    return (T(0) < val) - (val < T(0));
}
}  // anonymous namespace

CarTracker::CarTracker(const Race* race)
  : race_(race), radius_model_(&race_->track()), lane_length_model_(&race_->track()) {
  stats_file_.open ("bin/" + FLAGS_race_id + "/stats.csv");
  stats_file_ << "piece_index,start_lane,end_lane,radius,in_piece_distance,angle,velocity,throttle" << std::endl;
}

CarTracker::~CarTracker() {
  stats_file_.close();
}

CarState CarTracker::Predict(const CarState& state, const Command& command) {
  TurboState turbo_state = state.turbo_state();
  double throttle = command.ThrottleSet() ? command.throttle() : state.throttle();
  double effective_throttle = turbo_state.is_on() ? throttle * turbo_state.turbo().factor() : throttle;
  if (command.TurboSet()) {
    turbo_state.Enable();
  }
  turbo_state.Decrement();

  double velocity = velocity_model_.Predict(state.velocity(), effective_throttle);
  double piece_distance = state.position().piece_distance() + velocity;
  int lap = state.position().lap();
  int piece = state.position().piece();
  int start_lane = state.position().start_lane();
  int end_lane = state.position().end_lane();
  Switch switch_state = state.switch_state();

  // Is it next piece?
  double lane_length = lane_length_model_.Length(state.position());
  if (piece_distance > lane_length) {
    piece_distance = piece_distance - lane_length;
    piece++;
    if (piece >= race_->track().pieces().size()) {
      piece = 0;
      lap++;
    }

    if (race_->track().pieces()[piece].has_switch() && switch_state != Switch::kStay) {
      // TODO Determine what is left and right lane
      if (switch_state == Switch::kSwitchRight) {
        end_lane = start_lane + 1;
        if (end_lane >= race_->track().lanes().size()) {
          std::cerr << "Changed lane out of track!" << std::endl;
          end_lane = race_->track().lanes().size() - 1;
        }
      } else {
        end_lane = start_lane - 1;
        if (end_lane < 0) {
          std::cerr << "Changed lane to -1!" << std::endl;
          end_lane = 0;
        }
      }
      switch_state = Switch::kStay;
    } else {
      start_lane = end_lane;
    }
  }
  switch_state = command.SwitchSet() ? command.get_switch() : switch_state;

  double radius = radius_model_.Radius(state.position());
  double direction = -sgn(race_->track().pieces()[state.position().piece()].angle());
  double angle = drift_model_.Predict(
      state.position().angle(),
      state.previous_angle(),
      state.velocity(),
      radius,
      direction);

  Position position;
  position.set_piece_distance(piece_distance);
  position.set_lap(lap);
  position.set_piece(piece);
  position.set_start_lane(start_lane);
  position.set_end_lane(end_lane);
  position.set_angle(angle);

  return CarState(position, velocity, state.position().angle(), switch_state, throttle, turbo_state);
}

void CarTracker::Record(const Position& position) {
  bool bump = false;
  if (just_started_) {
    just_started_ = false;
    state_ = CarState(position);
  }

  // TODO Make sure everything works on crash.
  // TODO If velocity model is trained, it is probably better to use it for
  // velocity (because of unknown length of switches.
  // TODO Handle bumps with other cars, do not break models then.

  TurboState turbo_state = state_.turbo_state();
  double throttle = last_command_.ThrottleSet() ? last_command_.throttle() : state_.throttle();
  double effective_throttle = turbo_state.is_on() ? throttle * turbo_state.turbo().factor() : throttle;
  if (last_command_.TurboSet()) {
    turbo_state.Enable();
  }
  turbo_state.Decrement();

  Switch switch_state = last_command_.SwitchSet() ? last_command_.get_switch() : state_.switch_state();

  double velocity = 0;
  if (state_.position().piece() == position.piece()) {
    velocity = position.piece_distance() - state_.position().piece_distance();
  } else {
    bool lane_length_perfect = false;
    velocity = position.piece_distance() - state_.position().piece_distance() +
      lane_length_model_.Length(state_.position(), &lane_length_perfect);

    // Note: because of switches, it is better to use our model.
    if (!lane_length_perfect && velocity_model_.IsReady()) {
      velocity = velocity_model_.Predict(state_.velocity(), effective_throttle);
    }

    if (position.start_lane() != position.end_lane()) {
      switch_state = Switch::kStay;
    }
  }

  if (!bump) {
    double direction = -sgn(race_->track().pieces()[state_.position().piece()].angle());

    // Update models
    crash_model_.RecordSafeAngle(position.angle());
    // There is too many problems in between pieces (length of switches),
    // so do not take those measurements into account.
    if (state_.position().piece() == position.piece()) {
      velocity_model_.Record(velocity, state_.velocity(), effective_throttle);

      // Do not learn drift model on switches.
      if (state_.position().start_lane() == state_.position().end_lane()) {
        drift_model_.Record(
            position.angle(), state_.position().angle(), state_.previous_angle(),
            state_.velocity(), RadiusInPosition(state_.position()), direction);
      }
    }

    if (velocity_model_.IsReady()) {
      lane_length_model_.Record(state_.position(), position, velocity_model_.Predict(state_.velocity(), effective_throttle));
    }

    if (drift_model_.IsReady()) {
      crash_model_.RecordDriftModelReady();
      double r = drift_model_.EstimateRadius(position.angle(), state_.position().angle(), state_.previous_angle(),
          state_.velocity(), direction);

      double expected_angle = drift_model_.Predict(state_.position().angle(), state_.previous_angle(), state_.velocity(), r, direction);
      radius_model_.Record(state_.position(), r);
    }
  }

  state_ = CarState(position, velocity, state_.position().angle(), switch_state, throttle, turbo_state);
  LogState();
}

bool CarTracker::IsSafe(const CarState& state, const Command& command) {
  return IsSafe(Predict(state, command));
}

bool CarTracker::IsSafe(const CarState& state) {
  // TODO hardcoded
  double safe_speed = 3;

  auto s = state;
  while (s.velocity() > safe_speed) {
    if (!crash_model_.IsSafe(s.position().angle())) {
      return false;
    }
    s = Predict(s, Command(0));
  }
  return true;
}

bool CarTracker::IsReady() const {
  return velocity_model_.IsReady() && drift_model_.IsReady();
}

double CarTracker::RadiusInPosition(const Position& position) {
  return race_->track().LaneRadius(position.piece(), position.start_lane());
}

void CarTracker::LogState() {
  const auto& position = state_.position();

  stats_file_ << std::setprecision(std::numeric_limits<double>::digits10)
    << position.piece() << ","
    << position.start_lane() << ","
    << position.end_lane() << ","
    << race_->track().LaneRadius(position.piece(), position.start_lane()) << ","
    << position.piece_distance() << ","
    << state_.position().angle() << ","
    << state_.velocity() << ","
    << state_.throttle() << std::endl;
}

void CarTracker::RecordTurboAvailable(const game::Turbo& turbo) {
  state_.AddNewTurbo(turbo);
}

void CarTracker::RecordCarCrash() {
  auto crashed_state = Predict(state_, last_command_);
  crash_model_.RecordCarCrash(crashed_state.position().angle());
  Reset();
  stats_file_ << "CRASH" << std::endl;
}

CarState CarTracker::CreateCarState(const CarState& prev, const Position& position) const {
  double velocity = 0.0;
  if (prev.position().piece() == position.piece()) {
    velocity = position.piece_distance() - prev.position().piece_distance();
  } else {
    velocity = position.piece_distance() - prev.position().piece_distance() +
      lane_length_model_.Length(prev.position());
  }

  return CarState(position, velocity, prev.position().angle(), Switch::kStay, 0.0, prev.turbo_state());
}

}  // namespace game
<commit_msg>Maybe fix switch<commit_after>#include "game/car_tracker.h"
#include "gflags/gflags.h"

DECLARE_string(race_id);

namespace game {

namespace {
template <typename T> int sgn(T val) {
    return (T(0) < val) - (val < T(0));
}
}  // anonymous namespace

CarTracker::CarTracker(const Race* race)
  : race_(race), radius_model_(&race_->track()), lane_length_model_(&race_->track()) {
  stats_file_.open ("bin/" + FLAGS_race_id + "/stats.csv");
  stats_file_ << "piece_index,start_lane,end_lane,radius,in_piece_distance,angle,velocity,throttle" << std::endl;
}

CarTracker::~CarTracker() {
  stats_file_.close();
}

CarState CarTracker::Predict(const CarState& state, const Command& command) {
  TurboState turbo_state = state.turbo_state();
  double throttle = command.ThrottleSet() ? command.throttle() : state.throttle();
  double effective_throttle = turbo_state.is_on() ? throttle * turbo_state.turbo().factor() : throttle;
  if (command.TurboSet()) {
    turbo_state.Enable();
  }
  turbo_state.Decrement();

  double velocity = velocity_model_.Predict(state.velocity(), effective_throttle);
  double piece_distance = state.position().piece_distance() + velocity;
  int lap = state.position().lap();
  int piece = state.position().piece();
  int start_lane = state.position().start_lane();
  int end_lane = state.position().end_lane();
  Switch switch_state = state.switch_state();
  switch_state = command.SwitchSet() ? command.get_switch() : switch_state;

  // Is it next piece?
  double lane_length = lane_length_model_.Length(state.position());
  if (piece_distance > lane_length) {
    piece_distance = piece_distance - lane_length;
    piece++;
    if (piece >= race_->track().pieces().size()) {
      piece = 0;
      lap++;
    }

    if (race_->track().pieces()[piece].has_switch() && switch_state != Switch::kStay) {
      // TODO Determine what is left and right lane
      if (switch_state == Switch::kSwitchRight) {
        end_lane = start_lane + 1;
        if (end_lane >= race_->track().lanes().size()) {
          std::cerr << "Changed lane out of track!" << std::endl;
          end_lane = race_->track().lanes().size() - 1;
        }
      } else {
        end_lane = start_lane - 1;
        if (end_lane < 0) {
          std::cerr << "Changed lane to -1!" << std::endl;
          end_lane = 0;
        }
      }
      switch_state = Switch::kStay;
    } else {
      start_lane = end_lane;
    }
  }

  double radius = radius_model_.Radius(state.position());
  double direction = -sgn(race_->track().pieces()[state.position().piece()].angle());
  double angle = drift_model_.Predict(
      state.position().angle(),
      state.previous_angle(),
      state.velocity(),
      radius,
      direction);

  Position position;
  position.set_piece_distance(piece_distance);
  position.set_lap(lap);
  position.set_piece(piece);
  position.set_start_lane(start_lane);
  position.set_end_lane(end_lane);
  position.set_angle(angle);

  return CarState(position, velocity, state.position().angle(), switch_state, throttle, turbo_state);
}

void CarTracker::Record(const Position& position) {
  bool bump = false;
  if (just_started_) {
    just_started_ = false;
    state_ = CarState(position);
  }

  // TODO Make sure everything works on crash.
  // TODO If velocity model is trained, it is probably better to use it for
  // velocity (because of unknown length of switches.
  // TODO Handle bumps with other cars, do not break models then.

  TurboState turbo_state = state_.turbo_state();
  double throttle = last_command_.ThrottleSet() ? last_command_.throttle() : state_.throttle();
  double effective_throttle = turbo_state.is_on() ? throttle * turbo_state.turbo().factor() : throttle;
  if (last_command_.TurboSet()) {
    turbo_state.Enable();
  }
  turbo_state.Decrement();

  Switch switch_state = last_command_.SwitchSet() ? last_command_.get_switch() : state_.switch_state();

  double velocity = 0;
  if (state_.position().piece() == position.piece()) {
    velocity = position.piece_distance() - state_.position().piece_distance();
  } else {
    bool lane_length_perfect = false;
    velocity = position.piece_distance() - state_.position().piece_distance() +
      lane_length_model_.Length(state_.position(), &lane_length_perfect);

    // Note: because of switches, it is better to use our model.
    if (!lane_length_perfect && velocity_model_.IsReady()) {
      velocity = velocity_model_.Predict(state_.velocity(), effective_throttle);
    }

    if (position.start_lane() != position.end_lane()) {
      switch_state = Switch::kStay;
    }
  }

  if (!bump) {
    double direction = -sgn(race_->track().pieces()[state_.position().piece()].angle());

    // Update models
    crash_model_.RecordSafeAngle(position.angle());
    // There is too many problems in between pieces (length of switches),
    // so do not take those measurements into account.
    if (state_.position().piece() == position.piece()) {
      velocity_model_.Record(velocity, state_.velocity(), effective_throttle);

      // Do not learn drift model on switches.
      if (state_.position().start_lane() == state_.position().end_lane()) {
        drift_model_.Record(
            position.angle(), state_.position().angle(), state_.previous_angle(),
            state_.velocity(), RadiusInPosition(state_.position()), direction);
      }
    }

    if (velocity_model_.IsReady()) {
      lane_length_model_.Record(state_.position(), position, velocity_model_.Predict(state_.velocity(), effective_throttle));
    }

    if (drift_model_.IsReady()) {
      crash_model_.RecordDriftModelReady();
      double r = drift_model_.EstimateRadius(position.angle(), state_.position().angle(), state_.previous_angle(),
          state_.velocity(), direction);

      double expected_angle = drift_model_.Predict(state_.position().angle(), state_.previous_angle(), state_.velocity(), r, direction);
      radius_model_.Record(state_.position(), r);
    }
  }

  state_ = CarState(position, velocity, state_.position().angle(), switch_state, throttle, turbo_state);
  LogState();
}

bool CarTracker::IsSafe(const CarState& state, const Command& command) {
  return IsSafe(Predict(state, command));
}

bool CarTracker::IsSafe(const CarState& state) {
  // TODO hardcoded
  double safe_speed = 3;

  auto s = state;
  while (s.velocity() > safe_speed) {
    if (!crash_model_.IsSafe(s.position().angle())) {
      return false;
    }
    s = Predict(s, Command(0));
  }
  return true;
}

bool CarTracker::IsReady() const {
  return velocity_model_.IsReady() && drift_model_.IsReady();
}

double CarTracker::RadiusInPosition(const Position& position) {
  return race_->track().LaneRadius(position.piece(), position.start_lane());
}

void CarTracker::LogState() {
  const auto& position = state_.position();

  stats_file_ << std::setprecision(std::numeric_limits<double>::digits10)
    << position.piece() << ","
    << position.start_lane() << ","
    << position.end_lane() << ","
    << race_->track().LaneRadius(position.piece(), position.start_lane()) << ","
    << position.piece_distance() << ","
    << state_.position().angle() << ","
    << state_.velocity() << ","
    << state_.throttle() << std::endl;
}

void CarTracker::RecordTurboAvailable(const game::Turbo& turbo) {
  state_.AddNewTurbo(turbo);
}

void CarTracker::RecordCarCrash() {
  auto crashed_state = Predict(state_, last_command_);
  crash_model_.RecordCarCrash(crashed_state.position().angle());
  Reset();
  stats_file_ << "CRASH" << std::endl;
}

CarState CarTracker::CreateCarState(const CarState& prev, const Position& position) const {
  double velocity = 0.0;
  if (prev.position().piece() == position.piece()) {
    velocity = position.piece_distance() - prev.position().piece_distance();
  } else {
    velocity = position.piece_distance() - prev.position().piece_distance() +
      lane_length_model_.Length(prev.position());
  }

  return CarState(position, velocity, prev.position().angle(), Switch::kStay, 0.0, prev.turbo_state());
}

}  // namespace game
<|endoftext|>


<commit_before>/****************************************************************/
/*               DO NOT MODIFY THIS HEADER                      */
/* MOOSE - Multiphysics Object Oriented Simulation Environment  */
/*                                                              */
/*           (c) 2010 Battelle Energy Alliance, LLC             */
/*                   ALL RIGHTS RESERVED                        */
/*                                                              */
/*          Prepared by Battelle Energy Alliance, LLC           */
/*            Under Contract No. DE-AC07-05ID14517              */
/*            With the U. S. Department of Energy               */
/*                                                              */
/*            See COPYRIGHT for full restrictions               */
/****************************************************************/

#include "UserDataIO.h"
#include "UserObject.h"
#include <vector>

const unsigned int UserDataIO::file_version = 1;

struct MUDSHeader               // MOOSE User Data Storage
{
  char _id[4];                  // 4 letter ID
  unsigned int _file_version;   // file version
};

UserDataIO::UserDataIO(UserObjectWarehouse & ud_wh) :
    _userobject_wh(ud_wh)
{
}

UserDataIO::~UserDataIO()
{
}

void
UserDataIO::write(const std::string & file_name)
{
  std::ofstream out(file_name.c_str(), std::ios::out | std::ios::binary);

  // header
  MUDSHeader head;
  memcpy(head._id, "MUDS", 4);
  head._file_version = file_version;
  out.write((const char *) & head, sizeof(head));

  // save the number of user objects
  unsigned int n_objs = _userobject_wh.size();
  out.write((const char *) & n_objs, sizeof(n_objs));

  // loop over objects and save them
  std::vector<UserObject *> & uds = _userobject_wh.getObjects();
  for (std::vector<UserObject *>::iterator it = uds.begin(); it != uds.end(); ++it)
  {
    UserObject * uo = *it;

    // write out the name
    std::string name = uo->name();
    out.write(name.c_str(), name.length() + 1);                 // do not forget the trailing zero ;-)

    long pos = out.tellp();
    unsigned int size = 0;
    // write out the size
    out.write((const char *) & size, sizeof(size));
    // write out the data
    uo->store(out);
    long end = out.tellp();
    // go back and overwrite the size
    out.seekp(pos);
    size = end - pos - sizeof(size);
    out.write((const char *) & size, sizeof(size));
    // go at the and of the stream and continue
    out.seekp(end);
  }
}

void
UserDataIO::read(const std::string & file_name)
{
  std::ifstream in(file_name.c_str(), std::ios::in | std::ios::binary);

  // header
  MUDSHeader head;
  in.read((char *) & head, sizeof(head));

  // check the header
  if (!(head._id[0] == 'M' && head._id[1] == 'U' && head._id[2] == 'D' && head._id[3] == 'S'))
    mooseError("Corrupted user data restart file");
  // check the file version
  if (head._file_version > file_version)
    mooseError("Trying to restart from a newer file version - you need to update MOOSE");

  // load the number of user objects
  unsigned int n_objs = 0;
  in.read((char *) & n_objs, sizeof(n_objs));

  // loop over objects and save them
  for (unsigned int i = 0; i < n_objs; i++)
  {
    // FIXME: turn this into a function
    std::string name;
    char ch = 0;
    do {
      in.read(&ch, 1);
      if (ch != '\0')
        name += ch;
    } while (ch != '\0');

    // read the size
    unsigned int size = 0;
    // write out the size
    in.read((char *) & size, sizeof(size));

    if (_userobject_wh.hasUserObject(name))
    {
      // read the object
      UserObject * uo = _userobject_wh.getUserObjectByName(name);
      uo->load(in);
    }
    else
    {
      // we do not know the object, so we skip it
      in.seekg(size, std::ios::cur);
    }
  }
}
<commit_msg>Use C++ version of memcpy (#1152)<commit_after>/****************************************************************/
/*               DO NOT MODIFY THIS HEADER                      */
/* MOOSE - Multiphysics Object Oriented Simulation Environment  */
/*                                                              */
/*           (c) 2010 Battelle Energy Alliance, LLC             */
/*                   ALL RIGHTS RESERVED                        */
/*                                                              */
/*          Prepared by Battelle Energy Alliance, LLC           */
/*            Under Contract No. DE-AC07-05ID14517              */
/*            With the U. S. Department of Energy               */
/*                                                              */
/*            See COPYRIGHT for full restrictions               */
/****************************************************************/

#include "UserDataIO.h"
#include "UserObject.h"
#include <vector>
#include <cstring>

const unsigned int UserDataIO::file_version = 1;

struct MUDSHeader               // MOOSE User Data Storage
{
  char _id[4];                  // 4 letter ID
  unsigned int _file_version;   // file version
};

UserDataIO::UserDataIO(UserObjectWarehouse & ud_wh) :
    _userobject_wh(ud_wh)
{
}

UserDataIO::~UserDataIO()
{
}

void
UserDataIO::write(const std::string & file_name)
{
  std::ofstream out(file_name.c_str(), std::ios::out | std::ios::binary);

  // header
  MUDSHeader head;
  std::memcpy(head._id, "MUDS", 4);
  head._file_version = file_version;
  out.write((const char *) & head, sizeof(head));

  // save the number of user objects
  unsigned int n_objs = _userobject_wh.size();
  out.write((const char *) & n_objs, sizeof(n_objs));

  // loop over objects and save them
  std::vector<UserObject *> & uds = _userobject_wh.getObjects();
  for (std::vector<UserObject *>::iterator it = uds.begin(); it != uds.end(); ++it)
  {
    UserObject * uo = *it;

    // write out the name
    std::string name = uo->name();
    out.write(name.c_str(), name.length() + 1);                 // do not forget the trailing zero ;-)

    long pos = out.tellp();
    unsigned int size = 0;
    // write out the size
    out.write((const char *) & size, sizeof(size));
    // write out the data
    uo->store(out);
    long end = out.tellp();
    // go back and overwrite the size
    out.seekp(pos);
    size = end - pos - sizeof(size);
    out.write((const char *) & size, sizeof(size));
    // go at the and of the stream and continue
    out.seekp(end);
  }
}

void
UserDataIO::read(const std::string & file_name)
{
  std::ifstream in(file_name.c_str(), std::ios::in | std::ios::binary);

  // header
  MUDSHeader head;
  in.read((char *) & head, sizeof(head));

  // check the header
  if (!(head._id[0] == 'M' && head._id[1] == 'U' && head._id[2] == 'D' && head._id[3] == 'S'))
    mooseError("Corrupted user data restart file");
  // check the file version
  if (head._file_version > file_version)
    mooseError("Trying to restart from a newer file version - you need to update MOOSE");

  // load the number of user objects
  unsigned int n_objs = 0;
  in.read((char *) & n_objs, sizeof(n_objs));

  // loop over objects and save them
  for (unsigned int i = 0; i < n_objs; i++)
  {
    // FIXME: turn this into a function
    std::string name;
    char ch = 0;
    do {
      in.read(&ch, 1);
      if (ch != '\0')
        name += ch;
    } while (ch != '\0');

    // read the size
    unsigned int size = 0;
    // write out the size
    in.read((char *) & size, sizeof(size));

    if (_userobject_wh.hasUserObject(name))
    {
      // read the object
      UserObject * uo = _userobject_wh.getUserObjectByName(name);
      uo->load(in);
    }
    else
    {
      // we do not know the object, so we skip it
      in.seekg(size, std::ios::cur);
    }
  }
}
<|endoftext|>


<commit_before>/*
 * Copyright (c) Meta Platforms, Inc. and affiliates.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include <thrift/lib/cpp2/async/HTTPClientChannel.h>

#include <folly/io/async/AsyncTransport.h>
#include <folly/portability/GTest.h>

#include <folly/io/async/AsyncSocket.h>
#include <proxygen/httpserver/HTTPServer.h>
#include <proxygen/httpserver/ResponseBuilder.h>
#include <thrift/lib/cpp2/server/ThriftServer.h>
#include <thrift/lib/cpp2/test/gen-cpp2/TestService.h>
#include <thrift/lib/cpp2/transport/http2/common/HTTP2RoutingHandler.h>
#include <thrift/lib/cpp2/util/ScopedServerInterfaceThread.h>
#include <wangle/bootstrap/ServerBootstrap.h>
#include <wangle/channel/AsyncSocketHandler.h>
#include <wangle/channel/Handler.h>
#include <wangle/channel/Pipeline.h>

#include <boost/lexical_cast.hpp>

using namespace apache::thrift;
using namespace apache::thrift::concurrency;
using namespace apache::thrift::test;
using std::string;

class TestServiceHandler : public TestServiceSvIf {
 public:
  void sendResponse(string& _return, int64_t size) override {
    if (size >= 0) {
      usleep(size);
    }

    _return = "test" + boost::lexical_cast<std::string>(size);
  }
};

std::unique_ptr<HTTP2RoutingHandler> createHTTP2RoutingHandler(
    ThriftServer& server) {
  auto h2_options = std::make_unique<proxygen::HTTPServerOptions>();
  h2_options->threads = static_cast<size_t>(server.getNumIOWorkerThreads());
  h2_options->idleTimeout = server.getIdleTimeout();
  h2_options->shutdownOn = {SIGINT, SIGTERM};
  return std::make_unique<HTTP2RoutingHandler>(
      std::move(h2_options), server.getThriftProcessor(), server);
}

std::shared_ptr<BaseThriftServer> createHttpServer() {
  auto handler = std::make_shared<TestServiceHandler>();
  auto tm = ThreadManager::newSimpleThreadManager(1);
  tm->threadFactory(std::make_shared<PosixThreadFactory>());
  tm->start();
  auto server = std::make_shared<ThriftServer>();
  server->setAddress({"::1", 0});
  server->setInterface(handler);
  server->setNumIOWorkerThreads(1);
  server->setThreadManager(tm);
  server->addRoutingHandler(createHTTP2RoutingHandler(*server));
  return server;
}

TEST(HTTPClientChannelTest, Basic) {
  ScopedServerInterfaceThread runner(createHttpServer());
  auto const addr = runner.getAddress();

  folly::EventBase eb;
  folly::AsyncTransport::UniquePtr socket(new folly::AsyncSocket(&eb, addr));

  TestServiceAsyncClient client(
      HTTPClientChannel::newHTTP2Channel(std::move(socket)));

  std::string ret;
  client.sync_sendResponse(ret, 42);
  EXPECT_EQ(ret, "test42");
}

TEST(HTTPClientChannelTest, NoGoodChannel) {
  ScopedServerInterfaceThread runner(createHttpServer());
  auto const addr = runner.getAddress();

  folly::EventBase eb;
  folly::AsyncTransport::UniquePtr socket(new folly::AsyncSocket(&eb, addr));

  auto channel = HTTPClientChannel::newHTTP2Channel(std::move(socket));

  EXPECT_TRUE(channel->good());

  channel->getTransport()->close();

  EXPECT_FALSE(channel->good());
}
<commit_msg>Extend resource pools test coverage //thrift/lib/cpp2/test:HTTPClientChannelTest<commit_after>/*
 * Copyright (c) Meta Platforms, Inc. and affiliates.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#include <thrift/lib/cpp2/async/HTTPClientChannel.h>

#include <folly/io/async/AsyncTransport.h>
#include <folly/portability/GTest.h>

#include <folly/io/async/AsyncSocket.h>
#include <proxygen/httpserver/HTTPServer.h>
#include <proxygen/httpserver/ResponseBuilder.h>
#include <thrift/lib/cpp2/server/ThriftServer.h>
#include <thrift/lib/cpp2/test/gen-cpp2/TestService.h>
#include <thrift/lib/cpp2/transport/http2/common/HTTP2RoutingHandler.h>
#include <thrift/lib/cpp2/util/ScopedServerInterfaceThread.h>
#include <wangle/bootstrap/ServerBootstrap.h>
#include <wangle/channel/AsyncSocketHandler.h>
#include <wangle/channel/Handler.h>
#include <wangle/channel/Pipeline.h>

#include <boost/lexical_cast.hpp>

using namespace apache::thrift;
using namespace apache::thrift::concurrency;
using namespace apache::thrift::test;
using std::string;

class TestServiceHandler : public TestServiceSvIf {
 public:
  void sendResponse(string& _return, int64_t size) override {
    if (size >= 0) {
      usleep(size);
    }

    _return = "test" + boost::lexical_cast<std::string>(size);
  }
};

std::unique_ptr<HTTP2RoutingHandler> createHTTP2RoutingHandler(
    ThriftServer& server) {
  auto h2_options = std::make_unique<proxygen::HTTPServerOptions>();
  h2_options->threads = static_cast<size_t>(server.getNumIOWorkerThreads());
  h2_options->idleTimeout = server.getIdleTimeout();
  h2_options->shutdownOn = {SIGINT, SIGTERM};
  return std::make_unique<HTTP2RoutingHandler>(
      std::move(h2_options), server.getThriftProcessor(), server);
}

std::shared_ptr<BaseThriftServer> createHttpServer() {
  auto handler = std::make_shared<TestServiceHandler>();
  auto server = std::make_shared<ThriftServer>();
  server->setAddress({"::1", 0});
  server->setInterface(handler);
  server->setNumIOWorkerThreads(1);
  server->setThreadFactory(std::make_shared<PosixThreadFactory>());
  server->setThreadManagerType(BaseThriftServer::ThreadManagerType::SIMPLE);
  server->addRoutingHandler(createHTTP2RoutingHandler(*server));
  return server;
}

TEST(HTTPClientChannelTest, Basic) {
  ScopedServerInterfaceThread runner(createHttpServer());
  auto const addr = runner.getAddress();

  folly::EventBase eb;
  folly::AsyncTransport::UniquePtr socket(new folly::AsyncSocket(&eb, addr));

  TestServiceAsyncClient client(
      HTTPClientChannel::newHTTP2Channel(std::move(socket)));

  std::string ret;
  client.sync_sendResponse(ret, 42);
  EXPECT_EQ(ret, "test42");
}

TEST(HTTPClientChannelTest, NoGoodChannel) {
  ScopedServerInterfaceThread runner(createHttpServer());
  auto const addr = runner.getAddress();

  folly::EventBase eb;
  folly::AsyncTransport::UniquePtr socket(new folly::AsyncSocket(&eb, addr));

  auto channel = HTTPClientChannel::newHTTP2Channel(std::move(socket));

  EXPECT_TRUE(channel->good());

  channel->getTransport()->close();

  EXPECT_FALSE(channel->good());
}
<|endoftext|>


<commit_before>#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/objdetect/objdetect.hpp"
#include <opencv2/opencv.hpp>

#include <iostream>
#include <stdio.h>

#include "imagedetect.hpp"
#include "videoin_c920.hpp"
#include "track.hpp"

using namespace std;
using namespace cv;

void writeImage(const Mat &frame, const vector<Rect> &rects, size_t index, const char *path, int frameCounter);

int main( int argc, const char** argv )
{
   string windowName = "Capture - Face detection";
   string capPath;
   VideoIn *cap;
   const size_t detectMax = 10;
   const string frameOpt = "--frame=";
   double frameStart = 0.0;
   const size_t distanceListLength = 10;
   float distanceVal;
   float distanceList[distanceListLength] = {0};
   if (argc < 2)
   {
      // No arguments? Open default camera
      // and hope for the best
      cap = new VideoIn(0);
      capPath = "negative/2-11";
      windowName = "Camera 0";
   }
   else
   {
      // Read through command line args, extract
      // cmd line parameters and input filename
      int fileArgc;
      for (fileArgc = 1; fileArgc < argc; fileArgc++)
      {
	 if (frameOpt.compare(0, frameOpt.length(), argv[fileArgc], frameOpt.length()) == 0)
	    frameStart = (double)atoi(argv[fileArgc] + frameOpt.length());
	 else
	    break;
      }
      // Digit? Open camera
      if (isdigit(*argv[fileArgc]) && !strstr(argv[fileArgc],".jpg"))
      {
	 cap = new VideoIn(*argv[fileArgc] - '0');
	 capPath = "negative/2-11_" + (*argv[fileArgc] - '0');
	 stringstream ss;
	 ss << "Camera ";
	 ss << *argv[fileArgc] - '0';
	 windowName = ss.str();
      }
      else
      {
	 // Open file name
	 cap = new VideoIn(argv[fileArgc]);
	 if (cap->VideoCap())
	 {
	    cap->VideoCap()->set(CV_CAP_PROP_POS_FRAMES, frameStart);
	    cap->frameCounter(frameStart);
	 }
	 capPath = "negative/" + string(argv[fileArgc]).substr(string(argv[fileArgc]).rfind('/')+1);
	 windowName = argv[fileArgc];
      }
   }

   Mat frame;
   vector <Mat> images;

   bool pause = false;
   bool captureAll = false;
   bool tracking = true;

   string detectWindowName = "Detection Parameters";
   namedWindow(detectWindowName);
   createTrackbar ("Scale", detectWindowName, &scale, 50, NULL);
   createTrackbar ("Neighbors", detectWindowName, &neighbors, 50, NULL);
   createTrackbar ("Max Detect", detectWindowName, &maxDetectSize, 1000, NULL);

   const char *cascadeName = "../cascade_training/classifier_bin_6/cascade_oldformat_43.xml";
   // Use GPU code if hardware is detected, otherwise
   // fall back to CPU code
   BaseCascadeDetect *detectCascade;
   if (gpu::getCudaEnabledDeviceCount() > 0)
      detectCascade = new GPU_CascadeDetect(cascadeName);
   else
      detectCascade = new CPU_CascadeDetect(cascadeName);

   // Load the cascades
   if( !detectCascade->loaded() )
   {
      cerr << "--(!)Error loading " << cascadeName << endl;
      return -1;
   }

   if (!cap->getNextFrame(false, frame))
   {
      cerr << "Can not read frame from input" << endl;
      return 0;
   }

   // Minimum size of a bin at ~30 feet distance
   // TODO : Verify this once camera is calibrated
   minDetectSize = frame.cols * 0.04;

   // Create list of tracked objects
   TrackedObjectList binTrackingList(24.0, frame.cols);

   // Read the video stream
   int startFrame = cap->frameCounter() + 1;
   while(cap->getNextFrame(pause, frame))
   {
      //TODO : grab angle delta from robot
      // Adjust the position of all of the detected objects
      // to account for movement of the robot between frames
      double deltaAngle = 0.0;
      binTrackingList.adjustAngle(deltaAngle);

      // Apply the classifier to the frame
      vector<Rect> detectRects;
      vector<unsigned> detectDirections;
      detectCascade->cascadeDetect(frame, detectRects, detectDirections);

      images.clear();
      // Filter out images using threshold values -
      // since bins are green this could be used as a second pass
      // to get rid of false positives which aren't green enough
      vector <Rect> filteredRects;

      for( size_t i = 0; i < min(detectRects.size(), detectMax); i++ )
      {
	 for (int j = 0; j < detectRects.size(); j++) {
	    if (i != j) {
	      Rect intersection = detectRects[i] & detectRects[j];
	      if (intersection.width * intersection.height > 0)
	      if (abs((detectRects[i].width * detectRects[i].height) - (detectRects[j].width * detectRects[j].height)) < 2000)
		  if (intersection.width / intersection.height < 5 &&  intersection.width / intersection.height > 0) {
		     Rect lowestYVal;
		     int indexHighest;
		     if(detectRects[i].y < detectRects[j].y) {
			lowestYVal = detectRects[i]; //higher rectangle
			indexHighest = j;
		     }
		     else {
			lowestYVal = detectRects[j]; //higher rectangle
			indexHighest = i;
		     }
		     if(intersection.y > lowestYVal.y) {
			//cout << "found intersection" << endl;
			rectangle(frame, detectRects[indexHighest], Scalar(0,255,255), 3);
			detectRects.erase(detectRects.begin()+indexHighest);
			detectDirections.erase(detectDirections.begin()+indexHighest);
		     }
		  }
	    }
	 }
	 // Mark detected rectangle on image
	 Scalar rectColor;
	 switch (detectDirections[i])
	 {
	    case 1:
	       rectColor = Scalar(0,0,255);
	       break;
	    case 2:
	       rectColor = Scalar(0,255,0);
	       break;
	    case 4:
	       rectColor = Scalar(255,0,0);
	       break;
	    case 8:
	       rectColor = Scalar(255,255,0);
	       break;
	    default:
	       rectColor = Scalar(255,0,255);
	       break;
	 }

	 rectangle( frame, detectRects[i], rectColor, 3);
	 // Label each outlined image with a digit.  Top-level code allows
	 // users to save these small images by hitting the key they're labeled with
	 // This should be a quick way to grab lots of falsly detected images
	 // which need to be added to the negative list for the next
	 // pass of classifier training.
	 stringstream label;
	 label << i;
	 putText(frame, label.str(), Point(detectRects[i].x+10, detectRects[i].y+30),
	       FONT_HERSHEY_PLAIN, 2.0, Scalar(0, 0, 255));

	 // Process this detected rectangle - either update the nearest
	 // object or add it as a new one
	 binTrackingList.processDetect(detectRects[i]);
      }
      // Don't update to next frame if paused to prevent
      // objects missing from this frame to be aged out
      if (!pause)
	 binTrackingList.nextFrame();
      // Print detect status of live objects
      binTrackingList.print();

      if (tracking)
      {
	 // Grab info from detected objects, print it ou
	 vector<TrackedObjectDisplay> displayList;
	 binTrackingList.getDisplay(displayList);
	 for (size_t i = 0; i < displayList.size(); i++)
	 {
	    if (displayList[i].ratio < 0.15)
	       continue;

	    // Color moves from red to green (via brown, yuck)
	    // as the detected ratio goes up
	    Scalar rectColor(0, 255 * displayList[i].ratio, 255 * (1.0 - displayList[i].ratio));

	    // Highlight detected target
	    rectangle(frame, displayList[i].rect, rectColor, 3);

	    // Write detect ID, distance and angle data
	    putText(frame, displayList[i].id, Point(displayList[i].rect.x+25, displayList[i].rect.y+30), FONT_HERSHEY_PLAIN, 2.0, rectColor);
	    stringstream distLabel;
	    distLabel << "D=";
	    distLabel << displayList[i].distance;
	    putText(frame, distLabel.str(), Point(displayList[i].rect.x+10, displayList[i].rect.y+50), FONT_HERSHEY_PLAIN, 1.5, rectColor);
	    stringstream angleLabel;
	    angleLabel << "A=";
	    angleLabel << displayList[i].angle;
	    putText(frame, angleLabel.str(), Point(displayList[i].rect.x+10, displayList[i].rect.y+70), FONT_HERSHEY_PLAIN, 1.5, rectColor);
	 }
      }

      // Put an A on the screen if capture-all is enabled so
      // users can keep track of that toggle's mode
      if (captureAll)
	 putText(frame, "A", Point(25,25), FONT_HERSHEY_PLAIN, 2.5, Scalar(0, 255, 255));

      //-- Show what you got
      imshow( windowName, frame );

      // Process user IO
      char c = waitKey(5);
      if( c == 'c' ) { break; } // exit
      else if( c == 'q' ) { break; } // exit
      else if( c == 27 ) { break; } // exit
      else if( c == ' ') { pause = !pause; }
      else if( c == 'f')  // advance to next frame
      {
	 cap->getNextFrame(false, frame);
      }
      else if (c == 'A') // toggle capture-all
      {
	 captureAll = !captureAll;
      }
      else if (c == 'A') // toggle tracking info display
      {
	 captureAll = !captureAll;
      }
      else if (c == 'a') // save all detected images
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 for (size_t index = 0; index < detectRects.size(); index++)
	    writeImage(frameCopy, detectRects, index, capPath.c_str(), cap->frameCounter());
      }
      else if (c == 'p') // print frame number to screen
      {
	 cout << cap->frameCounter() << endl;
      }
      else if (isdigit(c)) // save a single detected image
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 writeImage(frameCopy, detectRects, c - '0', capPath.c_str(), cap->frameCounter());
      }
      if (captureAll && detectRects.size())
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 for (size_t index = 0; index < detectRects.size(); index++)
	    writeImage(frameCopy, detectRects, index, capPath.c_str(), cap->frameCounter());
      }
   }
   return 0;
}

void writeImage(const Mat &frame, const vector<Rect> &rects, size_t index, const char *path, int frameCounter)
{
   if (index < rects.size())
   {
      Mat image = frame(rects[index]);
      // Create filename, save image
      stringstream fn;
      fn << path;
      fn << "_";
      fn << frameCounter;
      fn << "_";
      fn << index;
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + ".png", image);

      // Save grayscale equalized version
      Mat frameGray;
      cvtColor( image, frameGray, CV_BGR2GRAY );
      equalizeHist( frameGray, frameGray );
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_g.png", frameGray);

      // Save 20x20 version of the same image
      Mat smallImg;
      resize(image, smallImg, Size(20,20));
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_s.png", smallImg);

      // Save grayscale equalized version of small image
      cvtColor( smallImg, frameGray, CV_BGR2GRAY );
      equalizeHist( frameGray, frameGray );
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_g_s.png", frameGray);
   }
}
<commit_msg>Fix toggle for tracking data<commit_after>#include "opencv2/highgui/highgui.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/objdetect/objdetect.hpp"
#include <opencv2/opencv.hpp>

#include <iostream>
#include <stdio.h>

#include "imagedetect.hpp"
#include "videoin_c920.hpp"
#include "track.hpp"

using namespace std;
using namespace cv;

void writeImage(const Mat &frame, const vector<Rect> &rects, size_t index, const char *path, int frameCounter);

int main( int argc, const char** argv )
{
   string windowName = "Capture - Face detection";
   string capPath;
   VideoIn *cap;
   const size_t detectMax = 10;
   const string frameOpt = "--frame=";
   double frameStart = 0.0;
   const size_t distanceListLength = 10;
   float distanceVal;
   float distanceList[distanceListLength] = {0};
   if (argc < 2)
   {
      // No arguments? Open default camera
      // and hope for the best
      cap = new VideoIn(0);
      capPath = "negative/2-11";
      windowName = "Camera 0";
   }
   else
   {
      // Read through command line args, extract
      // cmd line parameters and input filename
      int fileArgc;
      for (fileArgc = 1; fileArgc < argc; fileArgc++)
      {
	 if (frameOpt.compare(0, frameOpt.length(), argv[fileArgc], frameOpt.length()) == 0)
	    frameStart = (double)atoi(argv[fileArgc] + frameOpt.length());
	 else
	    break;
      }
      // Digit? Open camera
      if (isdigit(*argv[fileArgc]) && !strstr(argv[fileArgc],".jpg"))
      {
	 cap = new VideoIn(*argv[fileArgc] - '0');
	 capPath = "negative/2-11_" + (*argv[fileArgc] - '0');
	 stringstream ss;
	 ss << "Camera ";
	 ss << *argv[fileArgc] - '0';
	 windowName = ss.str();
      }
      else
      {
	 // Open file name
	 cap = new VideoIn(argv[fileArgc]);
	 if (cap->VideoCap())
	 {
	    cap->VideoCap()->set(CV_CAP_PROP_POS_FRAMES, frameStart);
	    cap->frameCounter(frameStart);
	 }
	 capPath = "negative/" + string(argv[fileArgc]).substr(string(argv[fileArgc]).rfind('/')+1);
	 windowName = argv[fileArgc];
      }
   }

   Mat frame;
   vector <Mat> images;

   bool pause = false;
   bool captureAll = false;
   bool tracking = true;

   string detectWindowName = "Detection Parameters";
   namedWindow(detectWindowName);
   createTrackbar ("Scale", detectWindowName, &scale, 50, NULL);
   createTrackbar ("Neighbors", detectWindowName, &neighbors, 50, NULL);
   createTrackbar ("Max Detect", detectWindowName, &maxDetectSize, 1000, NULL);

   const char *cascadeName = "../cascade_training/classifier_bin_6/cascade_oldformat_43.xml";
   // Use GPU code if hardware is detected, otherwise
   // fall back to CPU code
   BaseCascadeDetect *detectCascade;
   if (gpu::getCudaEnabledDeviceCount() > 0)
      detectCascade = new GPU_CascadeDetect(cascadeName);
   else
      detectCascade = new CPU_CascadeDetect(cascadeName);

   // Load the cascades
   if( !detectCascade->loaded() )
   {
      cerr << "--(!)Error loading " << cascadeName << endl;
      return -1;
   }

   if (!cap->getNextFrame(false, frame))
   {
      cerr << "Can not read frame from input" << endl;
      return 0;
   }

   // Minimum size of a bin at ~30 feet distance
   // TODO : Verify this once camera is calibrated
   minDetectSize = frame.cols * 0.04;

   // Create list of tracked objects
   TrackedObjectList binTrackingList(24.0, frame.cols);

   // Read the video stream
   int startFrame = cap->frameCounter() + 1;
   while(cap->getNextFrame(pause, frame))
   {
      //TODO : grab angle delta from robot
      // Adjust the position of all of the detected objects
      // to account for movement of the robot between frames
      double deltaAngle = 0.0;
      binTrackingList.adjustAngle(deltaAngle);

      // Apply the classifier to the frame
      vector<Rect> detectRects;
      vector<unsigned> detectDirections;
      detectCascade->cascadeDetect(frame, detectRects, detectDirections);

      images.clear();
      // Filter out images using threshold values -
      // since bins are green this could be used as a second pass
      // to get rid of false positives which aren't green enough
      vector <Rect> filteredRects;

      for( size_t i = 0; i < min(detectRects.size(), detectMax); i++ )
      {
	 for (int j = 0; j < detectRects.size(); j++) {
	    if (i != j) {
	      Rect intersection = detectRects[i] & detectRects[j];
	      if (intersection.width * intersection.height > 0)
	      if (abs((detectRects[i].width * detectRects[i].height) - (detectRects[j].width * detectRects[j].height)) < 2000)
		  if (intersection.width / intersection.height < 5 &&  intersection.width / intersection.height > 0) {
		     Rect lowestYVal;
		     int indexHighest;
		     if(detectRects[i].y < detectRects[j].y) {
			lowestYVal = detectRects[i]; //higher rectangle
			indexHighest = j;
		     }
		     else {
			lowestYVal = detectRects[j]; //higher rectangle
			indexHighest = i;
		     }
		     if(intersection.y > lowestYVal.y) {
			//cout << "found intersection" << endl;
			rectangle(frame, detectRects[indexHighest], Scalar(0,255,255), 3);
			detectRects.erase(detectRects.begin()+indexHighest);
			detectDirections.erase(detectDirections.begin()+indexHighest);
		     }
		  }
	    }
	 }
	 // Mark detected rectangle on image
	 Scalar rectColor;
	 switch (detectDirections[i])
	 {
	    case 1:
	       rectColor = Scalar(0,0,255);
	       break;
	    case 2:
	       rectColor = Scalar(0,255,0);
	       break;
	    case 4:
	       rectColor = Scalar(255,0,0);
	       break;
	    case 8:
	       rectColor = Scalar(255,255,0);
	       break;
	    default:
	       rectColor = Scalar(255,0,255);
	       break;
	 }

	 rectangle( frame, detectRects[i], rectColor, 3);
	 // Label each outlined image with a digit.  Top-level code allows
	 // users to save these small images by hitting the key they're labeled with
	 // This should be a quick way to grab lots of falsly detected images
	 // which need to be added to the negative list for the next
	 // pass of classifier training.
	 stringstream label;
	 label << i;
	 putText(frame, label.str(), Point(detectRects[i].x+10, detectRects[i].y+30),
	       FONT_HERSHEY_PLAIN, 2.0, Scalar(0, 0, 255));

	 // Process this detected rectangle - either update the nearest
	 // object or add it as a new one
	 binTrackingList.processDetect(detectRects[i]);
      }
      // Don't update to next frame if paused to prevent
      // objects missing from this frame to be aged out
      if (!pause)
	 binTrackingList.nextFrame();
      // Print detect status of live objects
      binTrackingList.print();

      if (tracking)
      {
	 // Grab info from detected objects, print it ou
	 vector<TrackedObjectDisplay> displayList;
	 binTrackingList.getDisplay(displayList);
	 for (size_t i = 0; i < displayList.size(); i++)
	 {
	    if (displayList[i].ratio < 0.15)
	       continue;

	    // Color moves from red to green (via brown, yuck)
	    // as the detected ratio goes up
	    Scalar rectColor(0, 255 * displayList[i].ratio, 255 * (1.0 - displayList[i].ratio));

	    // Highlight detected target
	    rectangle(frame, displayList[i].rect, rectColor, 3);

	    // Write detect ID, distance and angle data
	    putText(frame, displayList[i].id, Point(displayList[i].rect.x+25, displayList[i].rect.y+30), FONT_HERSHEY_PLAIN, 2.0, rectColor);
	    stringstream distLabel;
	    distLabel << "D=";
	    distLabel << displayList[i].distance;
	    putText(frame, distLabel.str(), Point(displayList[i].rect.x+10, displayList[i].rect.y+50), FONT_HERSHEY_PLAIN, 1.5, rectColor);
	    stringstream angleLabel;
	    angleLabel << "A=";
	    angleLabel << displayList[i].angle;
	    putText(frame, angleLabel.str(), Point(displayList[i].rect.x+10, displayList[i].rect.y+70), FONT_HERSHEY_PLAIN, 1.5, rectColor);
	 }
      }

      // Put an A on the screen if capture-all is enabled so
      // users can keep track of that toggle's mode
      if (captureAll)
	 putText(frame, "A", Point(25,25), FONT_HERSHEY_PLAIN, 2.5, Scalar(0, 255, 255));

      //-- Show what you got
      imshow( windowName, frame );

      // Process user IO
      char c = waitKey(5);
      if( c == 'c' ) { break; } // exit
      else if( c == 'q' ) { break; } // exit
      else if( c == 27 ) { break; } // exit
      else if( c == ' ') { pause = !pause; }
      else if( c == 'f')  // advance to next frame
      {
	 cap->getNextFrame(false, frame);
      }
      else if (c == 'A') // toggle capture-all
      {
	 captureAll = !captureAll;
      }
      else if (c == 't') // toggle tracking info display
      {
	 captureAll = !captureAll;
      }
      else if (c == 'a') // save all detected images
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 for (size_t index = 0; index < detectRects.size(); index++)
	    writeImage(frameCopy, detectRects, index, capPath.c_str(), cap->frameCounter());
      }
      else if (c == 'p') // print frame number to screen
      {
	 cout << cap->frameCounter() << endl;
      }
      else if (isdigit(c)) // save a single detected image
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 writeImage(frameCopy, detectRects, c - '0', capPath.c_str(), cap->frameCounter());
      }
      if (captureAll && detectRects.size())
      {
	 Mat frameCopy;
	 cap->getNextFrame(true, frameCopy);
	 for (size_t index = 0; index < detectRects.size(); index++)
	    writeImage(frameCopy, detectRects, index, capPath.c_str(), cap->frameCounter());
      }
   }
   return 0;
}

void writeImage(const Mat &frame, const vector<Rect> &rects, size_t index, const char *path, int frameCounter)
{
   if (index < rects.size())
   {
      Mat image = frame(rects[index]);
      // Create filename, save image
      stringstream fn;
      fn << path;
      fn << "_";
      fn << frameCounter;
      fn << "_";
      fn << index;
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + ".png", image);

      // Save grayscale equalized version
      Mat frameGray;
      cvtColor( image, frameGray, CV_BGR2GRAY );
      equalizeHist( frameGray, frameGray );
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_g.png", frameGray);

      // Save 20x20 version of the same image
      Mat smallImg;
      resize(image, smallImg, Size(20,20));
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_s.png", smallImg);

      // Save grayscale equalized version of small image
      cvtColor( smallImg, frameGray, CV_BGR2GRAY );
      equalizeHist( frameGray, frameGray );
      imwrite(fn.str().substr(fn.str().rfind('\\')+1) + "_g_s.png", frameGray);
   }
}
<|endoftext|>


<commit_before>// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/browser/shell_login_dialog.h"

#include "base/logging.h"
#include "base/strings/string16.h"
#include "base/strings/utf_string_conversions.h"
#include "content/nw/src/resource.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/resource_dispatcher_host.h"
#include "content/public/browser/resource_request_info.h"
#include "content/public/browser/web_contents.h"
#include "content/public/browser/web_contents_view.h"

namespace content {

INT_PTR CALLBACK ShellLoginDialog::DialogProc(HWND dialog,
                                              UINT message,
                                              WPARAM wparam,
                                              LPARAM lparam) {
  switch (message) {
    case WM_INITDIALOG: {
      SetWindowLongPtr(dialog, DWL_USER, static_cast<LONG_PTR>(lparam));
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(lparam);
      owner->dialog_win_ = dialog;
      SetDlgItemText(dialog,
                     IDC_DIALOG_MESSAGETEXT,
                     owner->message_text_.c_str());
      break;
    }
    case WM_CLOSE: {
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(
          GetWindowLongPtr(dialog, DWL_USER));
      owner->UserCancelledAuth();
      DestroyWindow(owner->dialog_win_);
      owner->dialog_win_ = NULL;
      break;
    }
    case WM_COMMAND: {
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(
          GetWindowLongPtr(dialog, DWL_USER));
      if (LOWORD(wparam) == IDOK) {
        string16 username;
        string16 password;
        size_t length =
            GetWindowTextLength(GetDlgItem(dialog, IDC_USERNAMEEDIT)) + 1;
        GetDlgItemText(dialog, IDC_USERNAMEEDIT,
                       WriteInto(&username, length), length);
        length = GetWindowTextLength(GetDlgItem(dialog, IDC_PASSWORDEDIT)) + 1;
        GetDlgItemText(dialog, IDC_PASSWORDEDIT,
                       WriteInto(&password, length), length);
        owner->UserAcceptedAuth(username, password);
      } else if (LOWORD(wparam) == IDCANCEL) {
        owner->UserCancelledAuth();
      } else {
        NOTREACHED();
      }

      break;
    }
    default:
      return DefWindowProc(dialog, message, wparam, lparam);
  }

  return 0;
}

void ShellLoginDialog::PlatformCreateDialog(const string16& message) {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));

  int render_process_id;
  int render_view_id;
  if (!ResourceRequestInfo::ForRequest(request_)->GetAssociatedRenderView(
          &render_process_id,  &render_view_id)) {
    NOTREACHED();
  }

  WebContents* web_contents = NULL;
  RenderViewHost* render_view_host =
      RenderViewHost::FromID(render_process_id, render_view_id);
  if (render_view_host)
    web_contents = WebContents::FromRenderViewHost(render_view_host);
  DCHECK(web_contents);

  gfx::NativeWindow parent_window =
      web_contents->GetView()->GetTopLevelNativeWindow();
  message_text_ = message;
  dialog_win_ = CreateDialogParam(GetModuleHandle(0),
                                  MAKEINTRESOURCE(IDD_LOGIN), parent_window,
                                  DialogProc, reinterpret_cast<LPARAM>(this));
  ShowWindow(dialog_win_, SW_SHOWNORMAL);
}

void ShellLoginDialog::PlatformCleanUp() {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  if (this->dialog_win_)
    DestroyWindow(this->dialog_win_);
}

void ShellLoginDialog::PlatformRequestCancelled() {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
}

}  // namespace content
<commit_msg>[WIN] support for login dialog queue<commit_after>// Copyright (c) 2012 Intel Corp
// Copyright (c) 2012 The Chromium Authors
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
//  in the Software without restriction, including without limitation the rights
//  to use, copy, modify, merge, publish, distribute, sublicense, and/or sell co
// pies of the Software, and to permit persons to whom the Software is furnished
//  to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in al
// l copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IM
// PLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNES
// S FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS
//  OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WH
// ETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
//  CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.

#include "content/nw/src/browser/shell_login_dialog.h"

#include "base/logging.h"
#include "base/strings/string16.h"
#include "base/strings/utf_string_conversions.h"
#include "content/nw/src/resource.h"
#include "content/public/browser/browser_thread.h"
#include "content/public/browser/render_view_host.h"
#include "content/public/browser/resource_dispatcher_host.h"
#include "content/public/browser/resource_request_info.h"
#include "content/public/browser/web_contents.h"
#include "content/public/browser/web_contents_view.h"

namespace content {

INT_PTR CALLBACK ShellLoginDialog::DialogProc(HWND dialog,
                                              UINT message,
                                              WPARAM wparam,
                                              LPARAM lparam) {
  switch (message) {
    case WM_INITDIALOG: {
      SetWindowLongPtr(dialog, DWL_USER, static_cast<LONG_PTR>(lparam));
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(lparam);
      owner->dialog_win_ = dialog;
      SetDlgItemText(dialog,
                     IDC_DIALOG_MESSAGETEXT,
                     owner->message_text_.c_str());
      break;
    }
    case WM_CLOSE: {
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(
          GetWindowLongPtr(dialog, DWL_USER));
      owner->UserCancelledAuth();
      DestroyWindow(owner->dialog_win_);
      owner->dialog_win_ = NULL;
      ReleaseSoon();
      break;
    }
    case WM_COMMAND: {
      ShellLoginDialog* owner = reinterpret_cast<ShellLoginDialog*>(
          GetWindowLongPtr(dialog, DWL_USER));
      if (LOWORD(wparam) == IDOK) {
        string16 username;
        string16 password;
        size_t length =
            GetWindowTextLength(GetDlgItem(dialog, IDC_USERNAMEEDIT)) + 1;
        GetDlgItemText(dialog, IDC_USERNAMEEDIT,
                       WriteInto(&username, length), length);
        length = GetWindowTextLength(GetDlgItem(dialog, IDC_PASSWORDEDIT)) + 1;
        GetDlgItemText(dialog, IDC_PASSWORDEDIT,
                       WriteInto(&password, length), length);
        owner->UserAcceptedAuth(username, password);
      } else if (LOWORD(wparam) == IDCANCEL) {
        owner->UserCancelledAuth();
      } else {
        NOTREACHED();
      }

      break;
    }
    default:
      return DefWindowProc(dialog, message, wparam, lparam);
  }

  return 0;
}

void ShellLoginDialog::PlatformCreateDialog(const string16& message) {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));

  int render_process_id;
  int render_view_id;
  if (!ResourceRequestInfo::ForRequest(request_)->GetAssociatedRenderView(
          &render_process_id,  &render_view_id)) {
    NOTREACHED();
  }

  WebContents* web_contents = NULL;
  RenderViewHost* render_view_host =
      RenderViewHost::FromID(render_process_id, render_view_id);
  if (render_view_host)
    web_contents = WebContents::FromRenderViewHost(render_view_host);
  DCHECK(web_contents);

  gfx::NativeWindow parent_window =
      web_contents->GetView()->GetTopLevelNativeWindow();
  message_text_ = message;
  dialog_win_ = CreateDialogParam(GetModuleHandle(0),
                                  MAKEINTRESOURCE(IDD_LOGIN), parent_window,
                                  DialogProc, reinterpret_cast<LPARAM>(this));
}

void ShellLoginDialog::PlatformShowDialog() {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  ShowWindow(dialog_win_, SW_SHOWNORMAL);
}

void ShellLoginDialog::PlatformCleanUp() {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
  if (dialog_win_) {
    DestroyWindow(dialog_win_);
    dialog_win_ = NULL;
  }
}

void ShellLoginDialog::PlatformRequestCancelled() {
  DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
}

}  // namespace content
<|endoftext|>