/******************************************************************************
 * Copyright (c) 2011 IBM Corporation
 * All rights reserved.
 * This program and the accompanying materials
 * are made available under the terms of the BSD License
 * which accompanies this distribution, and is available at
 * http://www.opensource.org/licenses/bsd-license.php
 *
 * Contributors:
 *     IBM Corporation - initial implementation
 *****************************************************************************/

#include <stdio.h>
#include <stdint.h>
#include <string.h>
#include <byteorder.h>
#include "p9.h"


/* Protocol stack marshaling. */
uint8_t *sp;

#define GET_08(s,i)	(s)[(i)]
#define GET_16(s,i)	le16_to_cpu(*(uint16_t*)(&(s)[(i)]))
#define GET_32(s,i)	le32_to_cpu(*(uint32_t*)(&(s)[(i)]))
#define GET_64(s,i)	le64_to_cpu(*(uint64_t*)(&(s)[(i)]))

#define SET_08(s,i,v)	(s)[(i)] = (v)
#define SET_16(s,i,v)	*(uint16_t*)(&(s)[(i)]) = cpu_to_le16(v)
#define SET_32(s,i,v)	*(uint32_t*)(&(s)[(i)]) = cpu_to_le32(v)
#define SET_64(s,i,v)	*(uint64_t*)(&(s)[(i)]) = cpu_to_le64(v)

#define PUT_08(v)	sp[0] = (v);sp+=1
#define PUT_16(v)	*(uint16_t*)(&sp[0]) = cpu_to_le16(v);sp+=2
#define PUT_32(v)	*(uint32_t*)(&sp[0]) = cpu_to_le32(v);sp+=4
#define PUT_64(v)	*(uint64_t*)(&sp[0]) = cpu_to_le64(v);sp+=8

#define PUT_HD(m,t)	PUT_32(0);PUT_08(m);PUT_16(t)
#define PUT_SN(v,n)	PUT_16(n);memcpy(sp,(v),(n));sp+=n
#define PUT_ST(v)	PUT_16(strlen(v));memcpy(sp,(v),strlen(v));\
				sp+=strlen(v)

#define GET_SIZE	(sp - tx)


/* General defines. */
#define MIN(a,b)	((a)>(b)?(b):(a))

#define NOTAG		((uint16_t)~0)
#define NOFID		((uint32_t)~0)
#define TAG		1
#define BUF_SIZE	(8*1024)

#define VERSION			"9P2000.u"
#define UNKNOWN_VER		"unknown"

#define MSG_SIZE		0
#define MSG_ID			4
#define MSG_ERR			0x6b
#define MSG_ERR_STR		9
#define MSG_ERR_STR_LEN		7
#define MSG_TAG			5
#define MSG_VER_MSIZE		7
#define MSG_VER_STR_LEN		11
#define MSG_VER_STR		13
#define MSG_WALK_TX_ELMT	15
#define MSG_WALK_RX_ELMT	7
#define MSG_SIZE		0
#define MSG_WALK_MAX_ELMT	16
#define MSG_QID_SIZE		13
#define MSG_WALK_RX_HDR_SIZE	9
#define MSG_OPEN_IOUNIT		20
#define MSG_OPEN_MODE_MASK	0x5f
#define MSG_READ_COUNT		7
#define MSG_READ_DATA		11
#define MSG_STAT_LEN		42
#define MSG_STAT_TYPE		17

#define T_VERSION	100
#define R_VERSION	(T_VERSION + 1)
#define T_ATTACH	104
#define R_ATTACH	(T_ATTACH + 1)
#define T_ERROR		106
#define R_ERROR		(T_ERROR + 1)
#define T_WALK		110
#define R_WALK		(T_WALK + 1)
#define T_OPEN		112
#define R_OPEN		(T_OPEN + 1)
#define T_READ		116
#define R_READ		(T_READ + 1)
#define T_CLUNK		120
#define R_CLUNK		(T_CLUNK + 1)
#define T_STAT		124
#define R_STAT		(T_STAT + 1)

static p9_transact_t transact;
static void *transact_opaque;
static uint8_t *tx;
static uint8_t *rx;


/**
 * p9_reg_transport
 *
 * Registers a transport function for use by the P9 protocol. The transport
 * connects the P9 Client (this library) to a server instance.
 *
 * @param transact_func[in]	Function pointer to type p9_transact_t.
 * @param tx_buffer[in]		TX buffer, must be 8k in size.
 * @param rx_buffer[in]		RX buffer, must be 8k in size.
 */
void p9_reg_transport(p9_transact_t transact_func, void *opaque,
		      uint8_t *tx_buffer, uint8_t *rx_buffer)
{
	transact = transact_func;
	transact_opaque = opaque;
	tx = tx_buffer;
	rx = rx_buffer;
}

/**
 * reset_buffers
 *
 * Reset the RX and TX buffers to BUF_SIZE (8k) and reset the Stack Pointer
 * for the TX buffer, which is referenced by the PUT_* macro's.
 */
void reset_buffers(void)
{
	memset(tx, 0, BUF_SIZE);
	memset(rx, 0, BUF_SIZE);
	sp = tx;
}

/**
 * p9_transaction
 *
 * Perform a transaction (send/recv) over the registered transport.
 *
 * @param connection[in|out]	Connection object.
 * @return	0 = success, -ve = error.
 */
int p9_transaction(p9_connection_t *connection)
{
	int rc;
	int tx_size = GET_SIZE;
	uint32_t rx_size = connection->message_size;

	if (transact == NULL) {
		return P9_NO_TRANSPORT;
	}
	if (tx == NULL || rx == NULL) {
		return P9_NO_BUFFER;
	}
	if (connection->message_size > BUF_SIZE) {
		return P9_MSG_SIZE_TOO_BIG;
	}
	if (tx_size > connection->message_size) {
		return P9_MSG_TOO_LONG;
	}

	SET_32(tx, MSG_SIZE, tx_size);
	rc = transact(transact_opaque, tx, tx_size, rx, &rx_size);

	if (rc != 0) {
		return P9_TRANSPORT_ERROR;
	}
	if (GET_16(tx, MSG_TAG) != GET_16(rx, MSG_TAG)) {
		return P9_UNEXPECTED_TAG;
	}
	if (GET_08(rx, MSG_ID) == MSG_ERR) {
		char error_string[200];

		memset(error_string, 0, 200);
		strncpy(error_string, (char *)&rx[MSG_ERR_STR],
				MIN(200 - 1, GET_16(rx, MSG_ERR_STR_LEN)));
#ifndef TEST
		printf("\nError: %s\n", error_string);
#endif
		return P9_R_ERROR;
	}
	if ((GET_08(tx, MSG_ID) + 1) != GET_08(rx, MSG_ID)) {
		return P9_UNEXPECTED_MSG;
	}

	return 0;
}

/**
 * p9_version
 *
 * Called to start a session. Negotiates the maximum message size for the
 * P9 protocol.
 *
 * @param connection[in|out]	Connection object, contains message_size.
 * @return	0 = success, -ve = error.
 *
 * @remark
 * size[4] Tversion tag[2] msize[4] version[s]
 * size[4] Rversion tag[2] msize[4] version[s]
 */
int p9_version(p9_connection_t *connection)
{
	int rc;
	char *ver_str;
	int ver_len;

	reset_buffers();

	/* Build message. */
	PUT_HD(T_VERSION, NOTAG);
	PUT_32(connection->message_size);
	PUT_ST(VERSION);

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}

	/* Handle response. */
	connection->message_size = MIN(connection->message_size,
			GET_32(rx, MSG_VER_MSIZE));

	ver_str = (char *)&rx[MSG_VER_STR];
	ver_len = GET_16(rx, MSG_VER_STR_LEN);
	if (strncmp(UNKNOWN_VER, ver_str, ver_len) == 0) {
		return P9_UNKNOWN_VERSION;
	}


	return 0;
}

/**
 * p9_attach
 *
 * Called to open a connection for a user to a file tree on the server. There
 * is no authorisation undertaken (NOFID).
 *
 * @param connection[in|out]	Connection object, contains uname and aname as
 * 	well as the connection fid and returned qid.
 * @return	0 = success, -ve = error.
 *
 * @remark
 * size[4] Tattach tag[2] fid[4] afid[4] uname[s] aname[s] n_uname[4]
 * size[4] Rattach tag[2] qid[13]
 */
int p9_attach(p9_connection_t *connection)
{
	int rc;
	int length = 19 + strlen(connection->uname) + strlen(connection->aname);

	if (length > connection->message_size) {
		return P9_MSG_TOO_LONG;
	}

	reset_buffers();

	/* Build message. */
	PUT_HD(T_ATTACH, TAG);
	PUT_32(connection->fid);	
	PUT_32(NOFID);
	PUT_ST(connection->uname);
	PUT_ST(connection->aname);
	PUT_32(~0); /* ??? */

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}


	return 0;
}

/**
 * p9_clunk
 *
 * Called when closing a file or connection (or after failed opens). Tells the
 * server that the supplied fid is no longer needed by this client.
 *
 * @param connection[in|out]	Connection object.
 * @param fid[in]	Fid to be clunked (released) on the server.
 * @return	0 = success, -ve = error.
 *
 * @remark
 * size[4] Tclunk tag[2] fid[4]
 * size[4] Rclunk tag[2]
 */
int p9_clunk(p9_connection_t *connection, uint32_t fid)
{
	int rc;

	reset_buffers();

	/* Build message. */
	PUT_HD(T_CLUNK, TAG);
	PUT_32(fid);

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}


	return 0;
}

/**
 * p9_walk
 *
 * Walk the provided path to a file (or directory) starting at the directory
 * indicated by fid and assigning new_fid to the last successfully walked
 * element. If not all elements of the path can be walked then the pos
 * pointer is set to the part of the path following the last successful
 * walked element. The function can be called again to walk the remainder
 * of the path (or produce an error).
 *
 * @param connection[in]	Connection object.
 * @param fid[in]	Fid to start walk from, must be directory or root (from
 * 	call to p9_attach).
 * @param new_fid[in]	Fid to be used for the last walked element.
 * @param pos[in|out]	Position in path that remains to be walked. If the
 * 	path was completely walked without error this will point to the NULL
 * 	at the end of path.
 * @return	1 = partial walk, 0 = success, -ve = error.
 *
 * @remark
 * size[4] Twalk tag[2] fid[4] newfid[4] nwname[2] nwname*(wname[s])
 * size[4] Rwalk tag[2] nwqid[2] nwqid*(qid[13])
 */
int p9_walk(p9_connection_t *connection, uint32_t fid, uint32_t new_fid,
		uint8_t **pos)
{
	int rc;
	const char *path = (const char *)*pos;
	uint8_t *s_tok;
	uint8_t *e_tok;
	int element_count = 0;

	if (path == NULL) {
		*pos = NULL;
		return P9_NULL_PATH;
	}

	reset_buffers();

	/* Build message. */
	PUT_HD(T_WALK, TAG);	/* Length to 0, set later. */
	PUT_32(fid);
	PUT_32(new_fid);
	PUT_16(0);		/* Element count to 0, set later. */

	/* Get elements from path, and append to message. */
	s_tok = (uint8_t *)path;
	e_tok = s_tok;

	while (*s_tok != 0) {
		while (*s_tok == '/') {
			s_tok++;
		}
		e_tok = s_tok;
		while ((*e_tok != '/') && (*e_tok != 0)) {
			e_tok++;
		}

		/* Check the element is OK. */
		if (strncmp(".", (const char *)s_tok, (e_tok - s_tok)) == 0) {
			/* Don't send ".", continue to next. */
			s_tok = e_tok;
			continue;
		}
		int tx_size = (e_tok - s_tok + 2 + GET_SIZE);
		int rx_size = ((element_count + 1) * MSG_QID_SIZE
				+ MSG_WALK_RX_HDR_SIZE);
		if ((tx_size > connection->message_size)
			|| (rx_size > connection->message_size)) {
			/*
			 * Element makes TX msg too long OR expected RX msg
			 * too long. Move pos to previous element and do
			 * partial walk.
			 */
			e_tok = s_tok;
			if (*(e_tok - 1) == '/') {
				e_tok--;
			}
			break;
		}

		/* Add the element to the message. */
		PUT_SN(s_tok, e_tok - s_tok);
		element_count++;

		/* Server supports no more than 16 elements, partial walk. */
		if (element_count == MSG_WALK_MAX_ELMT) {
			break;
		}

		/* Ready to find the next element. */
		s_tok = e_tok;
	}

	if ((element_count == 0) && (strlen(path) > 0)) {
		return P9_PATH_ELEMENT_TOO_LONG;
	}

	*pos = e_tok;

	/* Update counts and then send message. */
	SET_16(tx, MSG_WALK_TX_ELMT, element_count);
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}

	/* Check for special return conditions. */
	if (element_count != GET_16(rx, MSG_WALK_RX_ELMT)) {
		/* Find the last element successfully walked */
		s_tok = (uint8_t *)path;
		e_tok = s_tok;
		element_count = GET_16(rx, MSG_WALK_RX_ELMT);

		while (element_count--) {
			while (*s_tok == '/') {
				s_tok++;
			}

			e_tok = s_tok;

			while ((*e_tok != '/') && (*e_tok != 0)) {
				e_tok++;
			}

			s_tok = e_tok;
		}

		*pos = e_tok;
	}
	if (**pos != 0) {
		rc = P9_PARTIAL_WALK;
	}


	return rc;
}

/**
 * p9_open
 *
 * Opens the file represented by fid with associated mode bit mask. The iounit
 * size returned from the server is written to the connection object.
 *
 * @param file[in|out]	File object, contains fid for file.
 * @param mode[in]	Mode to open with. Bit's 0=R, 1=W, 2=RW, 3=EX, 4=Trunc
 * 	and 6=Delete on Close.
 * @return	0 = success, -ve = error.
 *
 * @remark
 * size[4] Topen tag[2] fid[4] mode[1]
 * size[4] Ropen tag[2] qid[13] iounit[4]
 */
int p9_open(p9_file_t *file, uint8_t mode)
{
	int rc;
	p9_connection_t *connection = file->connection;

	reset_buffers();
	file->iounit = 0;

	/* Build message. */
	PUT_HD(T_OPEN, TAG);
	PUT_32(file->fid);
	PUT_08(mode & MSG_OPEN_MODE_MASK);

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}

	/* Handle response. */
	file->iounit = GET_32(rx, MSG_OPEN_IOUNIT);


	return 0;
}

/**
 * p9_read
 *
 * Reads the file in to buffer.
 *
 * @param file[in]	File object, contains fid for file.
 * @param buffer[out]	Buffer for data.
 * @param count[in]	Number of bytes to read (less bytes than requested
 * 	 may be read).
 * @param offset[in]	Offset in file to read from.
 * @return	Bytes read, -ve = error.
 *
 * @remark
 * size[4] Tread tag[2] fid[4] offset[8] count[4]
 * size[4] Rread tag[2] count[4] data[count]
 */
int p9_read(p9_file_t *file, uint8_t *buffer,
		uint32_t count, uint64_t offset)
{
	int rc;
	p9_connection_t *connection = file->connection;
	uint32_t got;

	reset_buffers();
	count = MIN((connection->message_size - MSG_READ_DATA), count);

	/* Build message. */
	PUT_HD(T_READ, TAG);
	PUT_32(file->fid);
	PUT_64(offset);
	PUT_32(count);

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}
	got = GET_32(rx, MSG_READ_COUNT);
	if (got > count) {
		return P9_READ_UNEXPECTED_DATA;
	}

	/* Handle response. */
	memcpy(buffer, &rx[MSG_READ_DATA], got);

	return got;
}

/**
 * p9_stat
 *
 * Stat's the fid and writes the type and length to the file object.
 *
 * @param file[in|out]	File object, contains fid for file.
 * @return	0 = success, -ve = error.
 *
 * @remark
 * size[4] Tstat tag[2] fid[4]
 * size[4] Rstat tag[2] size[2] stat[n]
 */
int p9_stat(p9_file_t *file)
{
	int rc;
	p9_connection_t *connection = file->connection;

	reset_buffers();
	file->length = 0;
	file->type = 0;

	/* Build message. */
	PUT_HD(T_STAT, TAG);
	PUT_32(file->fid);

	/* Send message. */
	rc = p9_transaction(connection);
	if (rc != 0) {
		return rc;
	}

	/* Handle response. */
	file->length = GET_64(rx, MSG_STAT_LEN);
	file->type = GET_08(rx, MSG_STAT_TYPE);


	return 0;
}
