// Author Name: Matt Strapp // Date: 25 April 2022 // x500: strap012 #ifndef UTIL_H #define UTIL_H // Get your libraries here #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #define NAME "SERVER" #define ANON "ANON" #define LINE_SIZE 5000 // overkill #define BUF_LEN 12000000 // overkill #define MAX_REQUEST_SIZE 10000000 #define MIN_USERNAME_LEN 4 #define MAX_USERNAME_LEN 8 #define MIN_PASSWORD_LEN 4 #define MAX_PASSWORD_LEN 8 #define MAX_COMMAND_LEN 10 enum Command { REGISTER = 0, // [username] [password] Register a new account LOGIN = 1, // [username] [password] Log in with an existing account and enter // the chat room LOGOUT = 2, // Log out and leave the chat room SEND = 3, // [msg] Send a public message SEND2 = 4, // [username] [msg] Send a private message to a user SENDA = 5, // [msg] Send an anonymous public message SENDA2 = 6, // [username] [msg] Send an anonymous private message to a user SENDF = 7, // [local file] Send a file publicly SENDF2 = 8, // [username] [local file] Send a file to a user privately LIST = 9, // List all online users DELAY = 10, // [N] A special command that delays for N seconds before // executing the next command in the script GETF = 11, // [filename] Server telling clinet to request a file, clinet // requesting a file PING = 12, // Check that connection is still there, doesn't do anything else CONNECT = 13, // [unique id] Allows the server to identify specific users when // they are logged in multiple times INVALID = 15 // Used when no valid command is found }; enum LinkType { MESSAGE_LINK, FILE_LINK }; typedef unsigned char BYTE; typedef unsigned int DWORD; typedef unsigned short WORD; Command parse_command(char *line); bool isValidUsername(char *username); bool isValidPassword(char *password); void Error(const char *format, ...); void Log(const char *format, ...); void BigEndianToLittle(BYTE *buf, int &i); void LittleEndianToBig(int &i, BYTE *buf); const char *com2str(Command command); double timeDifference(struct timeb a, struct timeb b); int getNumEntries(const char *databse); bool loginQuery(const char *database, char *username, char *password); bool usernameQuery(const char *database, char *username); void recordEntry(const char *database, char *key, char *value); int buf2file(BYTE *buf, int nbytes, char *filename); int file2buf(char *filename, BYTE *buf); #define HEADER_LEN 13 // number of bytes in a message header enum Direction { C2S, S2C }; // client to server, server to client enum Flag { SUCCESS, FAIL }; // success, failure enum Recipient { PUB, PRIV }; // send to all, send to one enum Trace { SIGN, ANNON }; // send publically, send anonymously class Header { public: enum Direction m_direction; enum Flag m_flag; enum Recipient m_recipient; enum Trace m_trace; Command m_command; BYTE m_name[9]; int m_size; Header(); // constructor void encode(BYTE *buf); // encode message to buffer void decode(BYTE *buf); // decode buffer to message void setFlags(enum Direction direction, enum Flag flag, enum Recipient recipient, enum Trace trace); void displayContents(bool tab); // helper to print contents of class }; inline bool operator==(const Header &lhs, const Header &rhs) { bool result = true; result &= lhs.m_direction == rhs.m_direction; result &= lhs.m_flag == rhs.m_flag; result &= lhs.m_recipient == rhs.m_recipient; result &= lhs.m_trace == rhs.m_trace; result &= lhs.m_command == rhs.m_command; for (int i = 0; i < MAX_USERNAME_LEN; i++) result &= lhs.m_name[i] == rhs.m_name[i]; result &= lhs.m_size == rhs.m_size; return result; } inline bool operator!=(const Header &lhs, const Header &rhs) { return !(lhs == rhs); } #endif