<commit_before>#include "EthernetControl.h"
#include "pcap.h"
#include "logger.h"

#ifdef _WIN32
    #include <winsock2.h>
    #include <iphlpapi.h>
#else
	#include <arpa/inet.h>
#endif

#include <iostream>
#include <fstream>
#include <iomanip>
#include <chrono>
#include <set>
#include <algorithm>

using std::cout;
using std::endl;
using std::min;

#include <ctime>
#include <cstring>
#include <cmath>

vector<EthernetControl::EthernetDevInfo>  EthernetControl::pcapDevices_;
std::set<string> EthernetControl::APSunits_;
std::map<string, EthernetControl::EthernetDevInfo> EthernetControl::APS2device_;

MACAddr::MACAddr() : addr(MAC_ADDR_LEN, 0){}

MACAddr::MACAddr(const string & macStr){
	addr.resize(6,0);
	for(int cnt = 0; cnt < MAC_ADDR_LEN; cnt++) {
		// copy mac address from string
		sscanf(macStr.substr(3*cnt,2).c_str(), "%x", addr.begin()+cnt);
	}
}

MACAddr::MACAddr(const int & macAddrInt){
	//TODO
}

string MACAddr::to_string() const{
    ostringstream ss;
    for(const uint8_t curByte : addr){
        ss << std::hex << std::setfill('0') << std::setw(2) << static_cast<int>(curByte) << ":";
    }
    //remove the trailing ":"
    string myStr = ss.str();
    myStr.pop_back();
    return myStr;
}

APSEthernetPacket::APSEthernetPacket() : header{{}, {}, EthernetControl::APS_PROTO, 0, {0}, 0}, payload(0){};

APSEthernetPacket::APSEthernetPacket(const MACAddr & destMAC, const MACAddr & srcMAC, APSCommand_t command, const uint32_t & addr) :
		header{destMAC, srcMAC, EthernetControl::APS_PROTO, 0, command, addr}, payload(0){};

vector<uint8_t> APSEthernetPacket::serialize() const {
	/*
	 * Serialize a packet to a vector of bytes for tranmission.
	 * TODO: handle host to network byte ordering here
	 */
	vector<uint8_t> outVec;
	outVec.resize(NUM_HEADER_BYTES + payload.size());

	//Push on the destination and source mac address
	auto insertPt = outVec.begin();
	std::copy(header.dest.addr.begin(), header.dest.addr.end(), insertPt); insertPt += 6;
	std::copy(header.src.addr.begin(), header.src.addr.end(), insertPt); insertPt += 6;

	//Push on ethernet protocol
	std::copy(reinterpret_cast<const uint8_t *>(&header.frameType), reinterpret_cast<const uint8_t *>(&header.frameType)+2, insertPt); insertPt += 2;

	//Sequence number
	std::copy(reinterpret_cast<const uint8_t*>(&header.seqNum), reinterpret_cast<const uint8_t*>(&header.seqNum)+2, insertPt); insertPt += 2;

	//Command
	std::copy(reinterpret_cast<const uint8_t*>(&header.command), reinterpret_cast<const uint8_t*>(&header.command)+4, insertPt); insertPt += 4;

	//Address
	std::copy(reinterpret_cast<const uint8_t*>(&header.addr), reinterpret_cast<const uint8_t*>(&header.addr)+4, insertPt); insertPt += 4;

	//Data
	std::copy(payload.begin(), payload.end(), insertPt);

	return outVec;
}

bool EthernetControl::pcapRunning = false;

APSEthernetPacket EthernetControl::create_broadcast_packet(const MACAddr & srcMAC){
	/*
	 * Helper function to put together a broadcast packet that all APS units should respond to.
	 */
	APSEthernetPacket myPacket;

	//Put the broadcast FF:FF:FF:FF:FF:FF in the MAC destination address
	std::fill(myPacket.header.dest.addr.begin(), myPacket.header.dest.addr.end(), 0xFF);

	//Put the source MAC addresss
	myPacket.header.src = srcMAC;
	myPacket.header.command.cmd = APS_COMMAND_STATUS;
	myPacket.header.command.mode_stat = APS_STATUS_TEMP;
	myPacket.header.command.cnt = 0x10; //minimum length packet<commit_msg>Fix network byte ordering todo. Also fix broadcast command.<commit_after>#include "EthernetControl.h"
#include "pcap.h"
#include "logger.h"

#ifdef _WIN32
    #include <winsock2.h>
    #include <iphlpapi.h>
#else
	#include <arpa/inet.h>
#endif

#include <iostream>
#include <fstream>
#include <iomanip>
#include <chrono>
#include <set>
#include <algorithm>

using std::cout;
using std::endl;
using std::min;

#include <ctime>
#include <cstring>
#include <cmath>

vector<EthernetControl::EthernetDevInfo>  EthernetControl::pcapDevices_;
std::set<string> EthernetControl::APSunits_;
std::map<string, EthernetControl::EthernetDevInfo> EthernetControl::APS2device_;

MACAddr::MACAddr() : addr(MAC_ADDR_LEN, 0){}

MACAddr::MACAddr(const string & macStr){
	addr.resize(6,0);
	for(int cnt = 0; cnt < MAC_ADDR_LEN; cnt++) {
		// copy mac address from string
		sscanf(macStr.substr(3*cnt,2).c_str(), "%x", addr.begin()+cnt);
	}
}

MACAddr::MACAddr(const int & macAddrInt){
	//TODO
}

string MACAddr::to_string() const{
    ostringstream ss;
    for(const uint8_t curByte : addr){
        ss << std::hex << std::setfill('0') << std::setw(2) << static_cast<int>(curByte) << ":";
    }
    //remove the trailing ":"
    string myStr = ss.str();
    myStr.pop_back();
    return myStr;
}

APSEthernetPacket::APSEthernetPacket() : header{{}, {}, EthernetControl::APS_PROTO, 0, {0}, 0}, payload(0){};

APSEthernetPacket::APSEthernetPacket(const MACAddr & destMAC, const MACAddr & srcMAC, APSCommand_t command, const uint32_t & addr) :
		header{destMAC, srcMAC, EthernetControl::APS_PROTO, 0, command, addr}, payload(0){};

vector<uint8_t> APSEthernetPacket::serialize() const {
	/*
	 * Serialize a packet to a vector of bytes for transmission.
	 * Handle host to network byte ordering here
	 */
	vector<uint8_t> outVec;
	outVec.resize(NUM_HEADER_BYTES + payload.size());

	//Push on the destination and source mac address
	auto insertPt = outVec.begin();
	std::copy(header.dest.addr.begin(), header.dest.addr.end(), insertPt); insertPt += 6;
	std::copy(header.src.addr.begin(), header.src.addr.end(), insertPt); insertPt += 6;

	//Push on ethernet protocol
	uint16_t myuint16;
	uint8_t * start;
	start = reinterpret_cast<uint8_t*>(&myuint16);
	myuint16 = htons(header.frameType);
	std::copy(start, start+2, insertPt); insertPt += 2;

	//Sequence number
	myuint16 = htons(header.seqNum);
	std::copy(start, start+2, insertPt); insertPt += 2;

	//Command
	uint32_t myuint32;
	start = reinterpret_cast<uint8_t*>(&myuint32);
	myuint32 = htonl(header.command.packed);
	std::copy(start, start+4, insertPt); insertPt += 4;

	//Address
	myuint32 = htonl(header.addr);
	std::copy(start, start+4, insertPt); insertPt += 4;

	//Data
	std::copy(payload.begin(), payload.end(), insertPt);

	return outVec;
}

bool EthernetControl::pcapRunning = false;

APSEthernetPacket EthernetControl::create_broadcast_packet(const MACAddr & srcMAC){
	/*
	 * Helper function to put together a broadcast status packet that all APS units should respond to.
	 */
	APSEthernetPacket myPacket;

	//Put the broadcast FF:FF:FF:FF:FF:FF in the MAC destination address
	std::fill(myPacket.header.dest.addr.begin(), myPacket.header.dest.addr.end(), 0xFF);
	//Put the source MAC address
	myPacket.header.src = srcMAC;
	//Fill out the host register status command
	myPacket.header.command.ack = 0;
	myPacket.header.command.r_w = 1;
	myPacket.header.command.cmd = APS_COMMAND_STATUS;
	myPacket.header.command.mode_stat = APS_STATUS_HOST;
	myPacket.header.command.cnt = 0x10; //minimum length packet
{'fraction_non_alphanumeric': 0.15080275229357798, 'fraction_numerical': 0.015338302752293578, 'mean_word_length': 5.442289935364728, 'pattern_counts': {'":': 4, '<': 71, '<?xml version=': 0, '>': 49, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6334236', 'n_tokens_mistral': 2548, 'n_tokens_neox': 2438, 'n_words': 550}