Пример #1
0
int	ltpei_parse_extension(char **cursor, int *bytesRemaining, Lyst exts,
		unsigned int *extensionOffset)
{
	char			*initialCursor;
	LtpExtensionInbound	*extField;
	unsigned int		valueLength;

	CHKERR(cursor);
	CHKERR(*cursor);
	CHKERR(bytesRemaining);
	CHKERR(exts);
	if ((*bytesRemaining) < 1)
	{
		return 0;	/*	Corrupt.			*/
	}

	extField = MTAKE(sizeof(LtpExtensionInbound));
	if (extField == NULL)
	{
		return -1;	/*	Give up.			*/
	}

	initialCursor = *cursor;
	extField->offset = *extensionOffset;
	extField->tag = **cursor;
	(*cursor)++;
	(*bytesRemaining)--;
	extractSmallSdnv(&valueLength, cursor, bytesRemaining);
	if (valueLength == 0 || *bytesRemaining < valueLength)
	{
		return 0;	/*	Corrupt.			*/
	}

	extField->length = valueLength;
	extField->value = MTAKE(valueLength);
	if (extField->value == 0)
	{
		MRELEASE(extField);
		return -1;	/*	Give up.			*/
	}

	memcpy(extField->value, *cursor, valueLength);
	(*cursor) += valueLength;
	(*bytesRemaining) -= valueLength;
	if (lyst_insert_last(exts, extField) == NULL)
	{
		MRELEASE(extField->value);
		MRELEASE(extField);
		return -1;	/*	Give up.			*/
	}

	*extensionOffset += ((*cursor) - initialCursor);
	return 1;
}
Пример #2
0
Файл: udpts.c Проект: b/ION
static int	udpParseMamsEndpoint(MamsEndpoint *ep)
{
	char	*colon;
	char	hostName[MAXHOSTNAMELEN + 1];
	UdpTsep	tsep;

	if (ep == NULL || ep->ept == NULL)
	{
		errno = EINVAL;
		putErrmsg("udpts can't parse MAMS endpoint name.", NULL);
		return -1;
	}

	colon = strchr(ep->ept, ':');
	*colon = '\0';
	istrcpy(hostName, ep->ept, sizeof hostName);
	*colon = ':';
	tsep.portNbr = atoi(colon + 1);
	tsep.ipAddress = getInternetAddress(hostName);
	ep->tsep = MTAKE(sizeof(UdpTsep));
	if (ep->tsep == NULL)
	{
		putSysErrmsg("udpts can't record parsed MAMS endpoint name.",
				NULL);
		return -1;
	}

	memcpy((char *) (ep->tsep), (char *) &tsep, sizeof(UdpTsep));
//printf("parsed '%s' to port %d address %d.\n", ep->ept, tsep.portNbr,
//tsep.ipAddress);
	return 0;
}
Пример #3
0
/**
 * \brief Convenience function to build a data report.
 *
 * \author Ed Birrane
 *
 * \note
 *   - We shallow copy information into the message. So, don't release anything
 *     provided as an argument to this function.
 *
 * \return NULL - Failure
 * 		   !NULL - Created message.
 *
 * \param[in] time     The time when the report was created.
 * \param[in[ reports  The data reports.
 */
rpt_data_t *rpt_create_data(time_t time,
		                    Lyst reports,
		                    eid_t recipient)
{
	rpt_data_t *result = NULL;

	DTNMP_DEBUG_ENTRY("rpt_create_data","(%d,0x%x,%s)",
			          time, (unsigned long) reports, recipient.name);

	/* Step 0: Sanity Check. */
	if(reports == NULL)
	{
		DTNMP_DEBUG_ERR("rpt_create_data","Bad Args.",NULL);
		DTNMP_DEBUG_EXIT("rpt_create_data","->NULL",NULL);
		return NULL;
	}

	/* Step 1: Allocate the message. */
	if((result = (rpt_data_t*) MTAKE(sizeof(rpt_data_t))) == NULL)
	{
		DTNMP_DEBUG_ERR("rpt_create_data","Can't alloc %d bytes.",
				        sizeof(rpt_data_t));
		DTNMP_DEBUG_EXIT("rpt_create_data","->NULL",NULL);
		return NULL;
	}

	/* Step 2: Populate the message. */
	result->time = time;
	result->reports = reports;
	result->recipient = recipient;
	result->size = 0;

	DTNMP_DEBUG_EXIT("rpt_create_data","->0x%x",result);
	return result;
}
Пример #4
0
/**
 * \brief serializes a register agent message into a buffer.
 *
 * \author Ed Birrane
 *
 * \note The returned message must be de-allocated from the memory pool.
 *
 * \return NULL - Failure
 *         !NULL - The serialized message.
 *
 * \param[in]  msg  The message to serialize.
 * \param[out] len  The length of the serialized message.
 */
uint8_t *msg_serialize_reg_agent(adm_reg_agent_t *msg, uint32_t *len)
{
	Sdnv id;

	uint8_t *result = NULL;
	uint8_t *cursor = NULL;

	DTNMP_DEBUG_ENTRY("msg_serialize_reg_agent","(0x%x, 0x%x)",
			          (unsigned long)msg, (unsigned long) len);

	/* Step 0: Sanity Checks. */
	if((msg == NULL) || (len == NULL))
	{
		DTNMP_DEBUG_ERR("msg_serialize_reg_agent","Bad Args",NULL);
		DTNMP_DEBUG_EXIT("msg_serialize_reg_agent","->NULL",NULL);
		return NULL;
	}

	/*
	 * STEP 1: Figure out the size of the entire message. That includes the
	 *         length of the header, acl list, SDNV holding length, and data.
	 */
	int id_len = strlen(msg->agent_id.name);
	encodeSdnv(&id,id_len);
	*len = id.length + id_len;

	/* STEP 4: Allocate the serialized message. */
	if((result = (uint8_t*)MTAKE(*len)) == NULL)
	{
		DTNMP_DEBUG_ERR("msg_serialize_reg_agent","Can't alloc %d bytes", *len);
		*len = 0;

		DTNMP_DEBUG_EXIT("msg_serialize_reg_agent","->NULL",NULL);
		return NULL;
	}

	/* Step 5: Populate the serialized message. */
	cursor = result;

	memcpy(cursor, id.text, id.length);
	cursor += id.length;

	memcpy(cursor, msg->agent_id.name, id_len);
	cursor += id_len;

	/* Step 6: Last sanity check. */
	if((cursor - result) != *len)
	{
		DTNMP_DEBUG_ERR("msg_serialize_reg_agent","Wrote %d bytes but allcated %d",
				(unsigned long) (cursor - result), *len);
		*len = 0;
		MRELEASE(result);

		DTNMP_DEBUG_EXIT("msg_serialize_reg_agent","->NULL",NULL);
		return NULL;
	}

	DTNMP_DEBUG_EXIT("msg_serialize_reg_agent","->0x%x",(unsigned long)result);
	return result;
}
Пример #5
0
expr_result_t ltp_get_eng_all(Lyst params)
{
	datacol_entry_t *entry = (datacol_entry_t*)lyst_data(lyst_first(params));
	unsigned long val = 0;
	unsigned int engineId = 0;
	expr_result_t result;
	result.type = EXPR_TYPE_UINT32;

	/* \todo: Check for NULL entry here. */
	NmltpSpan span;
	int success = 0;

	memcpy(&val, entry->value, sizeof(val));
	engineId = val;

	result.length = 0;
	result.value = NULL;
	ltpnm_span_get(engineId, &span, &success);
	if(success != 0)
	{
		result.value = (uint8_t*) MTAKE(sizeof(span));
		memcpy(result.value, &span, sizeof(span));
		result.length = sizeof(span);
	}

	return result;
}
Пример #6
0
Файл: udpts.c Проект: b/ION
static int	udpParseAmsEndpoint(AmsEndpoint *dp)
{
	char	*colon;
	char	hostName[MAXHOSTNAMELEN + 1];
	UdpTsep	tsep;

	if (dp == NULL || dp->ept == NULL)
	{
		errno = EINVAL;
		putErrmsg("udpts can't parse AMS endpoint.", NULL);
		return -1;
	}

	colon = strchr(dp->ept, ':');
	*colon = '\0';
	istrcpy(hostName, dp->ept, sizeof hostName);
	*colon = ':';
	tsep.portNbr = atoi(colon + 1);
	tsep.ipAddress = getInternetAddress(hostName);
	dp->tsep = MTAKE(sizeof(UdpTsep));
	if (dp->tsep == NULL)
	{
		putSysErrmsg("udpts can't record parsed AMS endpoint name.",
				NULL);
		return -1;
	}

	memcpy((char *) (dp->tsep), (char *) &tsep, sizeof(UdpTsep));

	/*	Also parse out the QOS of this endpoint.		*/

	dp->diligence = AmsBestEffort;
	dp->sequence = AmsArrivalOrder;
	return 0;
}
Пример #7
0
uint8_t* adm_copy_string(char *value, uint64_t *length)
{
	uint8_t *result = NULL;
	uint32_t size = 0;

	DTNMP_DEBUG_ENTRY("adm_copy_string","(%#llx, %d, %#llx)", value, size, length);

	/* Step 0 - Sanity Check. */
	if((value == NULL) || (length == NULL))
	{
		DTNMP_DEBUG_ERR("adm_copy_string","Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_copy_string","->NULL.", NULL);
		return NULL;
	}

	size = strlen(value) + 1;
	/* Step 1 - Alloc new space. */
	if((result = (uint8_t *) MTAKE(size)) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_copy_string","Can't alloc %d bytes.", size);
		DTNMP_DEBUG_EXIT("adm_copy_string","->NULL.", NULL);
		return NULL;
	}

	/* Step 2 - Copy data in. */
	*length = size;
	memcpy(result, value, size);

	/* Step 3 - Return. */
	DTNMP_DEBUG_EXIT("adm_copy_string","->%s", (char *)result);
	return (uint8_t*)result;
}
Пример #8
0
/**
 * \brief Convenience function to build data report message.
 *
 * \author Ed Birrane
 *
 * \note
 *   - We shallow copy information into the message. So, don't release anything
 *     provided as an argument to this function.
 *
 * \return NULL - Failure
 * 		   !NULL - Created message.
 *
 * \param[in[ contents The data IDs available.
 */
rpt_items_t *rpt_create_lst(Lyst contents)
{
	rpt_items_t *result = NULL;

	DTNMP_DEBUG_ENTRY("rpt_create_lst","(0x%x)", (unsigned long) contents);

	/* Step 0: Sanity Check. */
	if(contents == NULL)
	{
		DTNMP_DEBUG_ERR("rpt_create_lst","Bad Args.",NULL);
		DTNMP_DEBUG_EXIT("rpt_create_lst","->NULL",NULL);
		return NULL;
	}

	/* Step 1: Allocate the message. */
	if((result = (rpt_items_t*)MTAKE(sizeof(rpt_items_t))) == NULL)
	{
		DTNMP_DEBUG_ERR("rpt_create_lst","Can't alloc %d bytes.",
				        sizeof(rpt_items_t));
		DTNMP_DEBUG_EXIT("rpt_create_lst","->NULL",NULL);
		return NULL;
	}

	/* Step 2: Populate the message. */
	result->contents = contents;

	DTNMP_DEBUG_EXIT("rpt_create_lst","->0x%x",result);
	return result;
}
Пример #9
0
mid_t *mid_copy(mid_t *src_mid)
{
    mid_t *result = 0;
    
    DTNMP_DEBUG_ENTRY("mid_copy","(%#llx)",
    		          (unsigned long) src_mid);
    
    /* Step 0: Sanity Check */
    if(src_mid == NULL)
    {
        DTNMP_DEBUG_ERR("mid_copy","Cannot copy from NULL source MID.", NULL);
        DTNMP_DEBUG_EXIT("mid_copy","->NULL",NULL);
        return NULL;
    }

    /* Step 1: Allocate the new MID. */
    if((result = (mid_t *)MTAKE(sizeof(mid_t))) == NULL)
    {
        DTNMP_DEBUG_ERR("mid_copy","Can't allocate %d bytes", sizeof(mid_t));
        DTNMP_DEBUG_EXIT("mid_copy","->NULL",NULL);
        return NULL;
    }

    /* Step 2: Start with a shallow copy. */
    memcpy(result, src_mid, sizeof(mid_t));

    /* Step 3: Now, deep copy the pointers. */
    result->oid = oid_copy(src_mid->oid);

    if((result->raw = (uint8_t *)MTAKE(src_mid->raw_size)) == NULL)
    {
        DTNMP_DEBUG_ERR("mid_copy","Can't allocate %d bytes",
        		        src_mid->raw_size);

        MRELEASE(result->oid);
        MRELEASE(result);

        DTNMP_DEBUG_EXIT("mid_copy","->NULL",NULL);
        return NULL;
    }

    memcpy(result->raw, src_mid->raw, src_mid->raw_size);

    DTNMP_DEBUG_EXIT("mid_copy","->%d", result);
    return result;
}
Пример #10
0
void adm_add_datadef(char *name,
		     	 	 uint8_t *mid_str,
		     	 	 int num_parms,
		     	 	 adm_string_fn to_string,
		     	 	 adm_size_fn get_size)
{
	uint32_t size = 0;
	uint32_t used = 0;
	adm_datadef_t *new_entry = NULL;

	DTNMP_DEBUG_ENTRY("adm_add_datadef","(%llx, %llx, %d, %llx, %llx)",
			          name, mid_str, num_parms, to_string, get_size);

	/* Step 0 - Sanity Checks. */
	if((name == NULL) || (mid_str == NULL))
	{
		DTNMP_DEBUG_ERR("adm_add_datadef","Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_add_datadef","->.", NULL);
		return;
	}
	if(gAdmData == NULL)
	{
		DTNMP_DEBUG_ERR("adm_add_datadef","Global data list not initialized.", NULL);
		DTNMP_DEBUG_EXIT("adm_add_datadef","->.", NULL);
		return;
	}

	/* Step 1 - Check name length. */
	if(strlen(name) > ADM_MAX_NAME)
	{
		DTNMP_DEBUG_WARN("adm_add_datadef","Trunc. %s to %d bytes.", name, ADM_MAX_NAME)
	}

	/* Step 2 - Allocate a Data Definition. */
	if((new_entry = (adm_datadef_t *) MTAKE(sizeof(adm_datadef_t))) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_add_datadef","Can't allocate new entry of size %d.",
				        sizeof(adm_datadef_t));
		DTNMP_DEBUG_EXIT("adm_add_datadef","->.", NULL);
		return;
	}

	/* Step 3 - Copy the ADM information. */
	strncpy((char *)new_entry->name, name, ADM_MAX_NAME);

	new_entry->mid = mid_deserialize(mid_str, ADM_MID_ALLOC, &used);

	new_entry->num_parms = num_parms;
	new_entry->collect = NULL;
	new_entry->to_string = (to_string == NULL) ? adm_print_uvast : to_string;
	new_entry->get_size = (get_size == NULL) ? adm_size_uvast : get_size;

	/* Step 4 - Add the new entry. */
	lyst_insert_last(gAdmData, new_entry);

	DTNMP_DEBUG_EXIT("adm_add_datadef","->.", NULL);
	return;
}
Пример #11
0
/******************************************************************************
 *
 * \par Function Name: adm_print_unsigned_long_list
 *
 * \par Generates a single string representation of a list of unsigned longs.
 *
 * \retval NULL Failure
 *         !NULL The string representation of the ADM entry value.
 *
 * \param[in]  buffer      The start of the ADM entry value.
 * \param[in]  buffer_len  Length of the given buffer.
 * \param[in]  data_len    Length of data item at head of the buffer.
 * \param[out] str_len     Length of returned string from print function.
 *
 * \par Notes:
 *		1. The string representation is allocated on the heap and must be
 *		   freed when no longer necessary.
 *
 * Modification History:
 *  MM/DD/YY  AUTHOR         DESCRIPTION
 *  --------  ------------   ---------------------------------------------
 *  11/25/12  E. Birrane     Initial implementation.
 *****************************************************************************/
char *adm_print_unsigned_long_list(uint8_t* buffer, uint64_t buffer_len, uint64_t data_len, uint32_t *str_len)
{
	char *result = NULL;
	char *cursor = NULL;
	uint8_t *buf_ptr = NULL;
	uvast num = 0;
	unsigned long val = 0;
	int len = 0;

	DTNMP_DEBUG_ENTRY("adm_print_unsigned_long_list", "(%#llx, %ull, %ull, %#llx)", buffer, buffer_len, data_len, str_len);

	/* Step 0 - Sanity Checks. */
	if((buffer == NULL) || (str_len == NULL))
	{
		DTNMP_DEBUG_ERR("adm_print_unsigned_long_list", "Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_print_unsigned_long_list", "->NULL.", NULL);
		return NULL;
	}

	/* Step 1 - Figure out how many unsigned longs we need to print out. */
	buf_ptr = buffer;
	len = decodeSdnv(&num, buf_ptr);
	buf_ptr += len;

	/* Step 2 - Size & allocate the string. */
	*str_len = data_len + /* Data length   */
		   9 +            /* Header info.    */
		   (2 * len) +    /* ", " per number */
		   1;             /* Trailer.        */

	if((result = (char *) MTAKE(*str_len)) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_print_unsigned_long_list", "Can't alloc %d bytes.",
				        *str_len);
		*str_len = 0;
		DTNMP_DEBUG_EXIT("adm_print_unsigned_long_list", "->NULL.", NULL);
		return NULL;
	}

	/* Step 3 - Accumulate string result. */
	cursor = result;

	cursor += sprintf(cursor,"("UVAST_FIELDSPEC"): ",num);

	int i;
	for(i = 0; i < num; i++)
	{
		memcpy(&val, buf_ptr, sizeof(val));
		buf_ptr += sizeof(val);
		cursor += sprintf(cursor, "%ld, ",val);
	}

	DTNMP_DEBUG_EXIT("adm_print_unsigned_long_list", "->%#llx.", result);
	return result;
}
Пример #12
0
void adm_add_ctrl(char *name,
				  uint8_t *mid_str,
				  int num_parms)
{
	uint8_t *tmp = NULL;
	uint32_t size = 0;
	uint32_t used = 0;
	adm_ctrl_t *new_entry = NULL;

	DTNMP_DEBUG_ENTRY("adm_add_ctrl","(%#llx, %#llx, %d)",
			          name, mid_str, num_parms);

	/* Step 0 - Sanity Checks. */
	if((name == NULL) || (mid_str == NULL))
	{
		DTNMP_DEBUG_ERR("adm_add_ctrl","Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_add_ctrl","->.", NULL);
		return;
	}
	if(gAdmCtrls == NULL)
	{
		DTNMP_DEBUG_ERR("adm_add_ctrl","Global Controls list not initialized.", NULL);
		DTNMP_DEBUG_EXIT("adm_add_ctrl","->.", NULL);
		return;
	}

	/* Step 1 - Check name length. */
	if(strlen(name) > ADM_MAX_NAME)
	{
		DTNMP_DEBUG_WARN("adm_add_ctrl","Trunc. %s to %d bytes.", name, ADM_MAX_NAME)
	}

	/* Step 2 - Allocate a Data Definition. */
	if((new_entry = (adm_ctrl_t *) MTAKE(sizeof(adm_ctrl_t))) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_add_ctrl","Can't allocate new entry of size %d.",
				        sizeof(adm_datadef_t));
		DTNMP_DEBUG_EXIT("adm_add_ctrl","->.", NULL);
		return;
	}

	/* Step 3 - Copy the ADM information. */
	strncpy((char *)new_entry->name, name, ADM_MAX_NAME);
	new_entry->mid = mid_deserialize(mid_str, ADM_MID_ALLOC, &used);

	//new_entry->mid_len = size;
	new_entry->num_parms = num_parms;
	new_entry->run = NULL;

	/* Step 4 - Add the new entry. */
	lyst_insert_last(gAdmCtrls, new_entry);

	DTNMP_DEBUG_EXIT("adm_add_ctrl","->.", NULL);
	return;
}
Пример #13
0
uint8_t *msg_serialize_rpt_policy(adm_rpt_policy_t *msg, uint32_t *len)
{
	uint8_t *result = NULL;
	uint8_t *cursor = NULL;

	DTNMP_DEBUG_ENTRY("msg_serialize_rpt_policy","(0x%x, 0x%x)",
			          (unsigned long)msg, (unsigned long) len);

	/* Step 0: Sanity Checks. */
	if((msg == NULL) || (len == NULL))
	{
		DTNMP_DEBUG_ERR("msg_serialize_rpt_policy","Bad Args",NULL);
		DTNMP_DEBUG_EXIT("msg_serialize_rpt_policy","->NULL",NULL);
		return NULL;
	}


	/*
	 * STEP 1: Figure out the size of the entire message. That includes the
	 *         length of the header, acl list, and 1 byte for the mask.
	 */
	*len = 1;

	/* STEP 4: Allocate the serialized message. */
	if((result = (uint8_t*)MTAKE(*len)) == NULL)
	{
		DTNMP_DEBUG_ERR("msg_serialize_rpt_policy","Can't alloc %d bytes", *len);
		*len = 0;

		DTNMP_DEBUG_EXIT("msg_serialize_rpt_policy","->NULL",NULL);
		return NULL;
	}

	/* Step 5: Populate the serialized message. */
	cursor = result;

	memcpy(cursor, &(msg->mask),1);
	cursor += 1;

	/* Step 6: Last sanity check. */
	if((cursor - result) != *len)
	{
		DTNMP_DEBUG_ERR("msg_serialize_rpt_policy","Wrote %d bytes but allcated %d",
				(unsigned long) (cursor - result), *len);
		*len = 0;
		MRELEASE(result);

		DTNMP_DEBUG_EXIT("msg_serialize_rpt_policy","->NULL",NULL);
		return NULL;
	}

	DTNMP_DEBUG_EXIT("msg_serialize_rpt_policy","->0x%x",(unsigned long)result);
	return result;
}
Пример #14
0
char *adm_print_string_list(uint8_t* buffer, uint64_t buffer_len, uint64_t data_len, uint32_t *str_len)
{
	char *result = NULL;
	char *cursor = NULL;
	uint8_t *buf_ptr = NULL;
	uvast num = 0;
	int len = 0;

	DTNMP_DEBUG_ENTRY("adm_print_string_list", "(%#llx, %ull, %ull, %#llx)", buffer, buffer_len, data_len, str_len);

	/* Step 0 - Sanity Checks. */
	if((buffer == NULL) || (str_len == NULL))
	{
		DTNMP_DEBUG_ERR("adm_print_string_list", "Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_print_string_list", "->NULL.", NULL);
		return NULL;
	}

	/* Step 1 - Figure out size of resulting string. */
	buf_ptr = buffer;
	len = decodeSdnv(&num, buf_ptr);
	buf_ptr += len;

	*str_len = data_len + /* String length   */
		   9 +            /* Header info.    */
		   (2 * len) +    /* ", " per string */
		   1;             /* Trailer.        */

	/* Step 2 - Allocate the result. */
	if((result = (char *) MTAKE(*str_len)) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_print_string_list","Can't alloc %d bytes", *str_len);

		*str_len = 0;
		DTNMP_DEBUG_EXIT("adm_print_string_list", "->NULL.", NULL);
		return NULL;
	}

	/* Step 3 - Accumulate the result. */
	cursor = result;

	cursor += sprintf(cursor,"("UVAST_FIELDSPEC"): ",num);

	/* Add stirngs to result. */
	int i;
	for(i = 0; i < num; i++)
	{
		cursor += sprintf(cursor, "%s, ",buf_ptr);
		buf_ptr += strlen((char*)buf_ptr) + 1;
	}

	DTNMP_DEBUG_EXIT("adm_print_string_list", "->%#llx.", result);
	return result;
}
Пример #15
0
Файл: udpts.c Проект: b/ION
static void	*udpAmsReceiver(void *parm)
{
	AmsInterface		*tsif = (AmsInterface *) parm;
	int			fd;
	AmsSAP			*amsSap;
	char			*buffer;
	sigset_t		signals;
	int			length;
	struct sockaddr_in	fromAddr;
	unsigned int		fromSize;

	fd = (long) (tsif->sap);
	amsSap = tsif->amsSap;
	buffer = MTAKE(UDPTS_MAX_MSG_LEN);
	if (buffer == NULL)
	{
		putSysErrmsg(NoMemoryMemo, NULL);
		return NULL;
	}

	sigfillset(&signals);
	pthread_sigmask(SIG_BLOCK, &signals, NULL);
	while (1)
	{
		fromSize = sizeof fromAddr;
		length = recvfrom(fd, buffer, UDPTS_MAX_MSG_LEN, 0,
				(struct sockaddr *) &fromAddr, &fromSize);
		if (length < 2)	/*	length == 1 is "shutdown"	*/
		{
			if (length < 0)
			{
				if (errno == EINTR)
				{
					continue;
				}

				putSysErrmsg("udpts failed receiving AMS \
message", NULL);
			}

			close(fd);
			MRELEASE(buffer);
			tsif->sap = NULL;
			return NULL;
		}

		/*	Got an AMS message.				*/

		if (enqueueAmsMsg(amsSap, (unsigned char *) buffer, length) < 0)
		{
			putErrmsg("udpts discarded AMS message.", NULL);
		}
	}
}
Пример #16
0
expr_result_t ltp_get_heap_bytes_used(Lyst params)
{
	unsigned long bytes_reserved = 0;
	unsigned long bytes_used = 0;
	expr_result_t result;
	result.type = EXPR_TYPE_UINT32;

	ltpnm_resources(&bytes_reserved, &bytes_used);
	result.length = sizeof(unsigned long);

	result.value = (uint8_t*) MTAKE(result.length);

	memcpy(result.value, &bytes_used, sizeof(bytes_used));
	return result;
}
Пример #17
0
/******************************************************************************
 *
 * \par Function Name: adm_print_uvast
 *
 * \par Generates a single string representation of a uvast.
 *
 * \retval NULL Failure
 *         !NULL The string representation of the ADM entry value.
 *
 * \param[in]  buffer      The start of the ADM entry value.
 * \param[in]  buffer_len  Length of the given buffer.
 * \param[in]  data_len    Length of data item at head of the buffer.
 * \param[out] str_len     Length of returned string from print function.
 *
 * \par Notes:
 *		1. The string representation is allocated on the heap and must be
 *		   freed when no longer necessary.
 *
 * Modification History:
 *  MM/DD/YY  AUTHOR         DESCRIPTION
 *  --------  ------------   ---------------------------------------------
 *  08/16/13  E. Birrane     Initial implementation.
 *****************************************************************************/
char *adm_print_uvast(uint8_t* buffer, uint64_t buffer_len,
		              uint64_t data_len, uint32_t *str_len)
{
  char *result;
  uint64_t temp = 0;

  DTNMP_DEBUG_ENTRY("adm_print_uvast", "(%#llx, %ull, %ull, %#llx)", buffer, buffer_len, data_len, str_len);

  /* Step 0 - Sanity Checks. */
  if((buffer == NULL) || (str_len == NULL))
  {
	  DTNMP_DEBUG_ERR("adm_print_uvast", "Bad Args.", NULL);
	  DTNMP_DEBUG_EXIT("adm_print_uvast", "->NULL.", NULL);
	  return NULL;
  }

  /* Step 1 - Make sure we have buffer space. */
  if(data_len > buffer_len)
  {
	 DTNMP_DEBUG_ERR("adm_print_uvast","Data Len %d > buf len %d.",
			         data_len, buffer_len);
	 *str_len = 0;

	 DTNMP_DEBUG_EXIT("adm_print_uvast", "->NULL.", NULL);
	 return NULL;
  }

  /* Step 2 - Size the string and allocate it.
   * \todo: A better estimate should go here. */
  *str_len = 32;

  if((result = (char *) MTAKE(*str_len)) == NULL)
  {
		 DTNMP_DEBUG_ERR("adm_print_uvast","Can't alloc %d bytes.",
				         *str_len);
		 *str_len = 0;

		 DTNMP_DEBUG_EXIT("adm_print_uvast", "->NULL.", NULL);
		 return NULL;
  }

  /* Step 3 - Copy data and return. */
  memcpy(&temp, buffer, data_len);
  isprintf(result,*str_len,UVAST_FIELDSPEC, temp);

  DTNMP_DEBUG_EXIT("adm_print_uvast", "->%#llx.", result);
  return result;
}
Пример #18
0
expr_result_t ltp_get_node_resources_all(Lyst params)
{
	unsigned long bytes_reserved = 0;
	unsigned long bytes_used = 0;
	expr_result_t result;
	result.type = EXPR_TYPE_BLOB;

	ltpnm_resources(&bytes_reserved, &bytes_used);
	result.length = sizeof(unsigned long) * 2;

	result.value = (uint8_t*) MTAKE(result.length);

	memcpy(result.value, &bytes_reserved, sizeof(bytes_reserved));
	memcpy(&(result.value[sizeof(bytes_reserved)]), &bytes_used, sizeof(bytes_used));
	return result;
}
Пример #19
0
/**
 * \brief Creates a report policy message from a buffer.
 *
 * \author Ed Birrane
 *
 * \note
 *   - On failure (NULL return) we do NOT de-allocate the passed-in header.
 *
 * \return NULL - failure
 *         !NULL - message.
 *
 * \param[in]  cursor      The buffer holding the message.
 * \param[in]  size        The remaining buffer size.
 * \param[out] bytes_used  Bytes consumed in the deserialization.
 */
adm_rpt_policy_t *msg_deserialize_rpt_policy(uint8_t *cursor,
        									 	 uint32_t size,
        									 	 uint32_t *bytes_used)
{
	adm_rpt_policy_t *result = NULL;
	uint32_t bytes = 0;

	DTNMP_DEBUG_ENTRY("msg_deserialize_rpt_policy","(0x%x, %d, 0x%x)",
			          (unsigned long)cursor, size,
			          (unsigned long) bytes_used);

	/* Step 0: Sanity Checks. */
	if((cursor == NULL) || (bytes_used == 0))
	{
		DTNMP_DEBUG_ERR("msg_deserialize_rpt_policy","Bad Args.",NULL);
		DTNMP_DEBUG_EXIT("msg_deserialize_rpt_policy","->NULL",NULL);
		return NULL;
	}

	/* Step 1: Allocate the new message structure. */
	if((result = (adm_rpt_policy_t*)MTAKE(sizeof(adm_rpt_policy_t))) == NULL)
	{
		DTNMP_DEBUG_ERR("msg_deserialize_rpt_policy","Can't Alloc %d Bytes.",
				        sizeof(adm_rpt_policy_t));
		*bytes_used = 0;
		DTNMP_DEBUG_EXIT("msg_deserialize_rpt_policy","->NULL",NULL);
		return NULL;
	}
	else
	{
		memset(result,0,sizeof(adm_rpt_policy_t));
	}

	/* Step 2: Deserialize the message. */

	/* Grab the mask */
	result->mask = *cursor;
	cursor++;
	size--;
	*bytes_used += 1;


	DTNMP_DEBUG_EXIT("msg_deserialize_rpt_policy","->0x%x",
			         (unsigned long)result);
	return result;
}
Пример #20
0
uint8_t *mid_serialize(mid_t *mid, uint32_t *size)
{
	uint8_t *result = NULL;

	DTNMP_DEBUG_ENTRY("mid_serialize","(%#llx, %#llx)",
			          (unsigned long) mid, (unsigned long) size);

	/* Step 0: Sanity Check. */
	if((mid == NULL) || (size == NULL))
	{
		DTNMP_DEBUG_ERR("mid_serialize","Bad args.", NULL);
		DTNMP_DEBUG_EXIT("mid_serialize","->NULL", NULL);
		return NULL;
	}

	/* Step 1: Make sure the MID is serialized. */
	if((mid->raw == NULL) || (mid->raw_size == 0))
	{
		if(mid_internal_serialize(mid) == 0)
		{
			DTNMP_DEBUG_ERR("mid_serialize","Can't serialize mid.", NULL);
			*size = 0;
			DTNMP_DEBUG_EXIT("mid_serialize","->NULL", NULL);
			return NULL;
		}
	}

	*size = mid->raw_size;

	/* Step 2: Allocate result. */
	if((result = (uint8_t*) MTAKE(*size)) == NULL)
	{
		DTNMP_DEBUG_ERR("mid_serialize","Can't alloc %d bytes.", *size);
		*size = 0;
		DTNMP_DEBUG_EXIT("mid_serialize","->NULL", NULL);
		return NULL;
	}

	/* Step 3: Copy in the result. */
	memcpy(result, mid->raw, mid->raw_size);

	DTNMP_DEBUG_EXIT("mid_serialize","->%#llx", (unsigned long)result);
	return result;
}
Пример #21
0
/******************************************************************************
 *
 * \par Function Name: adm_print_string
 *
 * \par Performs the somewhat straightforward function of building a string
 *      representation of a string. This is a generic to-string function for
 *      ADM entries whose values are strings.
 *
 * \retval NULL Failure
 *         !NULL The string representation of the ADM entry value.
 *
 * \param[in]  buffer      The start of the ADM entry value.
 * \param[in]  buffer_len  Length of the given buffer.
 * \param[in]  data_len    Length of data item at head of the buffer.
 * \param[out] str_len     Length of returned string from print function.
 *
 * \par Notes:
 *		1. The string representation is allocated on the heap and must be
 *		   freed when no longer necessary.
 *
 * Modification History:
 *  MM/DD/YY  AUTHOR         DESCRIPTION
 *  --------  ------------   ---------------------------------------------
 *  11/25/12  E. Birrane     Initial implementation.
 *****************************************************************************/
char *adm_print_string(uint8_t* buffer, uint64_t buffer_len, uint64_t data_len, uint32_t *str_len)
{
	char *result = NULL;
	uint32_t len = 0;

	DTNMP_DEBUG_ENTRY("adm_print_string","(%#llx, %ull, %ull, %#llx)", buffer, buffer_len, data_len, str_len);

	/* Step 0 - Sanity Checks. */
	if((buffer == NULL) || (str_len == NULL))
	{
		DTNMP_DEBUG_ERR("adm_print_string", "Bad Args.", NULL);
		DTNMP_DEBUG_EXIT("adm_print_string", "->NULL.", NULL);
		return NULL;
	}

	/* Step 1 - Data at head of buffer should be a string. Grab len & check. */
	len = strlen((char*) buffer);

	if((len > buffer_len) || (len != data_len))
	{
		DTNMP_DEBUG_ERR("adm_print_string", "Bad len %d. Expected %d.",
				        len, data_len);
		DTNMP_DEBUG_EXIT("adm_print_string", "->NULL.", NULL);
		return NULL;
	}

	/* Step 2 - Allocate size for string rep. of the string value. */
	*str_len = len + 1;
	if((result = (char *) MTAKE(*str_len)) == NULL)
	{
		DTNMP_DEBUG_ERR("adm_print_string", "Can't alloc %d bytes",
				        *str_len);
		DTNMP_DEBUG_EXIT("adm_print_string", "->NULL.", NULL);
		return NULL;
	}

	/* Step 3 - Copy over. */
	sprintf(result,"%s", (char*) buffer);

	DTNMP_DEBUG_EXIT("adm_print_string", "->%s.", result);

	return result;
}
Пример #22
0
expr_result_t ltp_get_engines(Lyst params)
{
	unsigned int ids[32];
	uint8_t *cursor = NULL;
	int num = 0;
	unsigned long val = 0;
	Sdnv num_sdnv;
	expr_result_t result;
	result.type = EXPR_TYPE_BLOB;

	ltpnm_spanEngineIds_get(ids, &num);
	if(num > 32)
	{
		fprintf(stderr,"We do not support more than 32 engines. Aborting.\n");
		exit(1);
	}

	encodeSdnv(&num_sdnv, num);

	result.length = num_sdnv.length +             /* NUM as SDNV length */
			  (num * sizeof(unsigned long));

	result.value = (uint8_t *) MTAKE(result.length);
	cursor = result.value;

	memcpy(cursor,num_sdnv.text, num_sdnv.length);
	cursor += num_sdnv.length;

	for(int i = 0; i < num; i++)
	{
		val = ids[i];
		memcpy(cursor,&val, sizeof(val));
		cursor += sizeof(val);
	}

	return result;
}
Пример #23
0
Файл: udpts.c Проект: b/ION
static int	udpMamsInit(MamsInterface *tsif)
{
	unsigned short		portNbr;
	unsigned int		ipAddress;
	char			hostName[MAXHOSTNAMELEN + 1];
	struct sockaddr		socketName;
	struct sockaddr_in	*inetName;
	socklen_t		nameLength;
	int			fd;
	char			endpointNameText[32];
	int			eptLen;
	long			longfd;

	parseSocketSpec(tsif->endpointSpec, &portNbr, &ipAddress);
//printf("parsed endpoint spec to port %d address %d.\n", portNbr, ipAddress);
	if (ipAddress == 0)
	{
		getNameOfHost(hostName, sizeof hostName);
		ipAddress = getInternetAddress(hostName);
	}
	else
	{
		if (getInternetHostName(ipAddress, hostName) == NULL)
		{
			putErrmsg("Unknown host in endpoint.",
					tsif->endpointSpec);
			return -1;
		}
	}

	portNbr = htons(portNbr);
	ipAddress = htonl(ipAddress);
	memset((char *) &socketName, 0, sizeof socketName);
	inetName = (struct sockaddr_in *) &socketName;
	inetName->sin_family = AF_INET;
	inetName->sin_port = portNbr;
	memcpy((char *) &(inetName->sin_addr.s_addr), (char *) &ipAddress, 4);
	fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
	if (fd < 0)
	{
		putSysErrmsg("udpts can't open MAMS SAP", NULL);
		return -1;
	}

	nameLength = sizeof(struct sockaddr);
	if (reUseAddress(fd)
	|| bind(fd, &socketName, nameLength) < 0
	|| getsockname(fd, &socketName, &nameLength) < 0)
	{
		putSysErrmsg("udpts can't initialize AMS SAP", NULL);
		return -1;
	}

	portNbr = inetName->sin_port;
	portNbr = ntohs(portNbr);
	memcpy((char *) &ipAddress, (char *) &(inetName->sin_addr.s_addr), 4);
	ipAddress = ntohl(ipAddress);
	isprintf(endpointNameText, sizeof endpointNameText, "%s:%hu", hostName,
			portNbr);
//printf("resulting ept is '%s'.\n", endpointNameText);
	eptLen = strlen(endpointNameText) + 1;
	tsif->ept = MTAKE(eptLen);
	if (tsif->ept == NULL)
	{
		close(fd);
		putSysErrmsg(NoMemoryMemo, NULL);
		return -1;
	}

	istrcpy(tsif->ept, endpointNameText, eptLen);
	longfd = fd;
	tsif->sap = (void *) longfd;
	return 0;
}
Пример #24
0
static void	*handleDatagrams(void *parm)
{
	/*	Main loop for UDP datagram reception and handling.	*/

	ReceiverThreadParms	*rtp = (ReceiverThreadParms *) parm;
	char			*procName = "udplsi";
	char			*buffer;
	int			segmentLength;
	struct sockaddr_in	fromAddr;
	socklen_t		fromSize;

	snooze(1);	/*	Let main thread become interruptable.	*/
	buffer = MTAKE(UDPLSA_BUFSZ);
	if (buffer == NULL)
	{
		putErrmsg("udplsi can't get UDP buffer.", NULL);
		ionKillMainThread(procName);
		return NULL;
	}

	/*	Can now start receiving bundles.  On failure, take
	 *	down the LSI.						*/

	while (rtp->running)
	{	
		fromSize = sizeof fromAddr;
		segmentLength = irecvfrom(rtp->linkSocket, buffer, UDPLSA_BUFSZ,
				0, (struct sockaddr *) &fromAddr, &fromSize);
		switch (segmentLength)
		{
		case -1:
			putSysErrmsg("Can't acquire segment", NULL);
			ionKillMainThread(procName);

			/*	Intentional fall-through to next case.	*/

		case 1:				/*	Normal stop.	*/
			rtp->running = 0;
			continue;
		}

		if (ltpHandleInboundSegment(buffer, segmentLength) < 0)
		{
			putErrmsg("Can't handle inbound segment.", NULL);
			ionKillMainThread(procName);
			rtp->running = 0;
			continue;
		}

		/*	Make sure other tasks have a chance to run.	*/

		sm_TaskYield();
	}

	writeErrmsgMemos();
	writeMemo("[i] udplsi receiver thread has ended.");

	/*	Free resources.						*/

	MRELEASE(buffer);
	return NULL;
}
Пример #25
0
static int	handleGreenSegment(AcqWorkArea *work, LtpSessionId *sessionId,
			unsigned char endOfBlock, unsigned int offset,
			unsigned int length, Object zco, unsigned int *buflen,				char **buffer)
{
	Sdr			sdr = getIonsdr();
	static LtpSessionId	currentSessionId = { 0, 0 };
	static unsigned int	currentOffset = 0;
	unsigned int		fillLength;
	ZcoReader		reader;
	int			result;

	if (zco == 0)		/*	Import session canceled.	*/
	{
		bpCancelAcq(work);
		currentSessionId.sourceEngineId = 0;
		currentSessionId.sessionNbr = 0;
		currentOffset = 0;
		return 0;
	}

	if (zco_source_data_length(sdr, zco) != length)
	{
		return 0;	/*	Just discard the segment.	*/
	}

	if (sessionId->sourceEngineId != currentSessionId.sourceEngineId
	|| sessionId->sessionNbr != currentSessionId.sessionNbr)
	{
		/*	Did not receive end-of-block segment for the
		 *	block that was being received.  Discard the
		 *	partially received bundle in the work area,
		 *	if any.						*/

		bpCancelAcq(work);
		currentSessionId.sourceEngineId = 0;
		currentSessionId.sessionNbr = 0;
		currentOffset = 0;
	}

	if (currentOffset == 0)
	{
		/*	Start new green bundle acquisition.		*/

		if (bpBeginAcq(work, 0, NULL) < 0)
		{
			putErrmsg("Can't begin acquisition of bundle.", NULL);
			return -1;
		}

		currentSessionId.sourceEngineId = sessionId->sourceEngineId;
		currentSessionId.sessionNbr = sessionId->sessionNbr;
	}

	if (offset < currentOffset)	/*	Out of order.		*/
	{
		return 0;	/*	Just discard the segment.	*/
	}

	if (offset > currentOffset)
	{
		/*	Convergence layer must not deliver incomplete
		 *	bundles to BP.  Practically speaking, this
		 *	gap in segment sequence must be treated as
		 *	malformation of the bundle.			*/

		work->malformed = 1;

		/*	But continue bundle acquisition anyway, in
		 *	case the incomplete bundle is useful for some
		 *	diagnostic purpose.				*/

		fillLength = offset - currentOffset;
		if (fillLength > *buflen)
		{
			/*	Make buffer big enough for the fill
			 *	data.					*/

			if (*buffer)
			{
				MRELEASE(*buffer);
				*buflen = 0;
			}

			*buffer = MTAKE(fillLength);
			if (*buffer == NULL)
			{
				/*	Gap is too large to fill.
				 *	Might be a DOS attack; cancel
				 *	acquisition.			*/

				bpCancelAcq(work);
				currentSessionId.sourceEngineId = 0;
				currentSessionId.sessionNbr = 0;
				currentOffset = 0;
				return 0;
			}

			*buflen = fillLength;
		}

		memset(*buffer, 0, fillLength);
		if (bpContinueAcq(work, *buffer, (int) fillLength, 0) < 0)
		{
			putErrmsg("Can't insert bundle fill data.", NULL);
			return -1;
		}

		currentOffset += fillLength;
	}

	if (length > *buflen)
	{
		/*	Make buffer big enough for the green data.	*/

		if (*buffer)
		{
			MRELEASE(*buffer);
			*buflen = 0;
		}

		*buffer = MTAKE(length);
		if (*buffer == NULL)
		{
			/*	Segment is too large.  Might be a
			 *	DOS attack; cancel acquisition.		*/

			bpCancelAcq(work);
			currentSessionId.sourceEngineId = 0;
			currentSessionId.sessionNbr = 0;
			currentOffset = 0;
			return 0;
		}

		*buflen = length;
	}

	/*	Extract data from segment ZCO so that it can be
	 *	appended to the bundle acquisition ZCO.  Note
	 *	that we're breaking the "zero-copy" model here;
	 *	it would be better to have an alternate version
	 *	of bpContinueAcq that uses zco_clone_source_data
	 *	to append the segment ZCO's source data to the
	 *	acquisition ZCO in the work area. (TODO)		*/

	zco_start_receiving(zco, &reader);
	CHKERR(sdr_begin_xn(sdr));
	result = zco_receive_source(sdr, &reader, length, *buffer);
	if (sdr_end_xn(sdr) < 0 || result < 0)
	{
		putErrmsg("Failed reading green segment data.", NULL);
		return -1;
	}

	if (bpContinueAcq(work, *buffer, (int) length, 0) < 0)
	{
		putErrmsg("Can't continue bundle acquisition.", NULL);
		return -1;
	}

	currentOffset += length;
	if (endOfBlock)
	{
		if (bpEndAcq(work) < 0)
		{
			putErrmsg("Can't end acquisition of bundle.", NULL);
			return -1;
		}

		currentSessionId.sourceEngineId = 0;
		currentSessionId.sessionNbr = 0;
		currentOffset = 0;
	}

	return 0;
}
Пример #26
0
Файл: libbp.c Проект: b/ION
int	bp_open(char *eidString, BpSAP *bpsapPtr)
{
	Sdr		sdr;
	MetaEid		metaEid;
	VScheme		*vscheme;
	PsmAddress	vschemeElt;
	Sap		sap;
	VEndpoint	*vpoint;
	PsmAddress	vpointElt;

	CHKERR(eidString && *eidString && bpsapPtr);
	*bpsapPtr = NULL;	/*	Default, in case of failure.	*/
	sdr = getIonsdr();
	sdr_begin_xn(sdr);	/*	Just to lock memory.		*/

	/*	First validate the endpoint ID.				*/

	if (parseEidString(eidString, &metaEid, &vscheme, &vschemeElt) == 0)
	{
		sdr_exit_xn(sdr);
		putErrmsg("Malformed EID.", eidString);
		return -1;
	}

	if (vschemeElt == 0)
	{
		sdr_exit_xn(sdr);
		putErrmsg("Scheme not known.", metaEid.schemeName);
		restoreEidString(&metaEid);
		return -1;
	}

	findEndpoint(NULL, metaEid.nss, vscheme, &vpoint, &vpointElt);
	if (vpointElt == 0)
	{
		sdr_exit_xn(sdr);
		putErrmsg("Endpoint not known.", metaEid.nss);
		restoreEidString(&metaEid);
		return -1;
	}

	/*	Endpoint exists; make sure it's not already opened
	 *	by some application.					*/

	if (vpoint->appPid > 0)	/*	Endpoint not closed.		*/
	{
		if (sm_TaskExists(vpoint->appPid))
		{
			sdr_exit_xn(sdr);
			if (vpoint->appPid == sm_TaskIdSelf())
			{
				return 0;
			}

			restoreEidString(&metaEid);
			putErrmsg("Endpoint is already open.",
					itoa(vpoint->appPid));
			return -1;
		}

		/*	Application terminated without closing the
		 *	endpoint, so simply close it now.		*/

		vpoint->appPid = -1;
	}

	/*	Construct the service access point.			*/

	sap.vpoint = vpoint;
	memcpy(&sap.endpointMetaEid, &metaEid, sizeof(MetaEid));
	sap.endpointMetaEid.colon = NULL;
	sap.endpointMetaEid.schemeName = MTAKE(metaEid.schemeNameLength + 1);
	if (sap.endpointMetaEid.schemeName == NULL)
	{
		sdr_exit_xn(sdr);
		putErrmsg("Can't create BpSAP.", NULL);
		restoreEidString(&metaEid);
		return -1;
	}

	sap.endpointMetaEid.nss = MTAKE(metaEid.nssLength + 1);
	if (sap.endpointMetaEid.nss == NULL)
	{
		sdr_exit_xn(sdr);
		MRELEASE(sap.endpointMetaEid.schemeName);
		putErrmsg("Can't create BpSAP.", NULL);
		restoreEidString(&metaEid);
		return -1;
	}

	*bpsapPtr = MTAKE(sizeof(Sap));
	if (*bpsapPtr == NULL)
	{
		sdr_exit_xn(sdr);
		MRELEASE(sap.endpointMetaEid.nss);
		MRELEASE(sap.endpointMetaEid.schemeName);
		putErrmsg("Can't create BpSAP.", NULL);
		restoreEidString(&metaEid);
		return -1;
	}

	istrcpy(sap.endpointMetaEid.schemeName, metaEid.schemeName,
			sizeof sap.endpointMetaEid.schemeName);
	istrcpy(sap.endpointMetaEid.nss, metaEid.nss,
			sizeof sap.endpointMetaEid.nss);
	restoreEidString(&metaEid);
	sap.recvSemaphore = vpoint->semaphore;
	memcpy((char *) *bpsapPtr, (char *) &sap, sizeof(Sap));

	/*	Having created the SAP, give its owner exclusive
	 *	access to the endpoint.					*/

	vpoint->appPid = sm_TaskIdSelf();
	sdr_exit_xn(sdr);	/*	Unlock memory.			*/
	return 0;
}
Пример #27
0
Файл: udpts.c Проект: b/ION
static int	udpAmsInit(AmsInterface *tsif, char *epspec)
{
	unsigned short		portNbr;
	unsigned int		ipAddress;
	char			hostName[MAXHOSTNAMELEN + 1];
	struct sockaddr		socketName;
	struct sockaddr_in	*inetName;
	socklen_t		nameLength;
	int			fd;
	char			endpointNameText[32];
	int			eptLen;
	long			longfd;

	if (strcmp(epspec, "@") == 0)	/*	Default.		*/
	{
		epspec = NULL;	/*	Force default selection.	*/
	}

	parseSocketSpec(epspec, &portNbr, &ipAddress);
	if (ipAddress == 0)
	{
		getNameOfHost(hostName, sizeof hostName);
		ipAddress = getInternetAddress(hostName);
	}
	else
	{
		if (getInternetHostName(ipAddress, hostName) == NULL)
		{
			putErrmsg("Unknown host in endpoint.", epspec);
			return -1;
		}
	}

	portNbr = htons(portNbr);
	ipAddress = htonl(ipAddress);
	memset((char *) &socketName, 0, sizeof socketName);
	inetName = (struct sockaddr_in *) &socketName;
	inetName->sin_family = AF_INET;
	inetName->sin_port = portNbr;
	memcpy((char *) &(inetName->sin_addr.s_addr), (char *) &ipAddress, 4);
	fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
	if (fd < 0)
	{
		putSysErrmsg("udpts can't open AMS SAP", NULL);
		return -1;
	}

	nameLength = sizeof(struct sockaddr);
	if (reUseAddress(fd)
	|| bind(fd, &socketName, nameLength) < 0
	|| getsockname(fd, &socketName, &nameLength) < 0)
	{
		putSysErrmsg("udpts can't initialize AMS SAP", NULL);
		return -1;
	}

	portNbr = inetName->sin_port;
	portNbr = ntohs(portNbr);
	memcpy((char *) &ipAddress, (char *) &(inetName->sin_addr.s_addr), 4);
	ipAddress = ntohl(ipAddress);
	tsif->diligence = AmsBestEffort;
	tsif->sequence = AmsArrivalOrder;
	isprintf(endpointNameText, sizeof endpointNameText, "%s:%hu", hostName,
			portNbr);
	eptLen = strlen(endpointNameText) + 1;
	tsif->ept = MTAKE(eptLen);
	if (tsif->ept == NULL)
	{
		close(fd);
		putSysErrmsg(NoMemoryMemo, NULL);
		return -1;
	}

	istrcpy(tsif->ept, endpointNameText, eptLen);
	longfd = fd;
	tsif->sap = (void *) longfd;
	return 0;
}
Пример #28
0
static void	*sendKeepalives(void *parm)
{
	KeepaliveThreadParms	*parms = (KeepaliveThreadParms *) parm;
	int			keepaliveTimer = 0;
	int			bytesSent;
	int			backoffTimer = BACKOFF_TIMER_START;
	int 			backoffTimerCount = 0;
	unsigned char 		*buffer;

	buffer = MTAKE(TCPCLA_BUFSZ);	//To send keepalive bundle
	if (buffer == NULL)
	{
		putErrmsg("No memory for TCP buffer in tcpclo.", NULL);
		return NULL;
	}

	iblock(SIGTERM);
	while (*(parms->cloRunning))
	{
		snooze(1);
		keepaliveTimer++;
		if (keepaliveTimer < *(parms->keepalivePeriod))
		{
			continue;
		}

		// If the negotiated keep alive interval is 0, then
		// keep alives will not be sent.
		if(*(parms->keepalivePeriod) == 0)
		{
			continue;
		}

		/*	Time to send a keepalive.  Note that the
		 *	interval between keepalive attempts will be
		 *	KEEPALIVE_PERIOD plus (if the remote induct
		 *	is not reachable) the length of time taken
		 *	by TCP to determine that the connection
		 *	attempt will not succeed (e.g., 3 seconds).	*/

		keepaliveTimer = 0;
		pthread_mutex_lock(parms->mutex);
		bytesSent = sendBundleByTCPCL(parms->socketName,
				parms->ductSocket, 0, 0, buffer, parms->keepalivePeriod);
		pthread_mutex_unlock(parms->mutex);
		/*	if the node is unable to establish a TCP connection,
 		 * 	the connection should be tried only after some delay.
 		 *								*/
		if(bytesSent == 0)
		{	
			while((backoffTimerCount < backoffTimer) && (*(parms->ductSocket) < 0))
			{
				snooze(1);
				backoffTimerCount++;
				if(!(*(parms->cloRunning)))
				{
					break;
				}
			}
			backoffTimerCount = 0;
			/*	keepaliveTimer keeps track of when the keepalive needs 
			 *	to be sent. This value is set to keepalive period.
			 *	That way at the end of backoff period a 
			 *	keepalive is sent
			 *							*/
			keepaliveTimer = *(parms->keepalivePeriod);

			if(backoffTimer < BACKOFF_TIMER_LIMIT)
			{
				backoffTimer *= 2;
			}
			continue;
		}
		backoffTimer = BACKOFF_TIMER_START;
		if (bytesSent < 0)
		{
			shutDownClo();
			break;
		}
	}
	MRELEASE(buffer);
	return NULL;
}
Пример #29
0
int	tcpclo(int a1, int a2, int a3, int a4, int a5,
		int a6, int a7, int a8, int a9, int a10)
{
	char	*ductName = (char *) a1;
#else
int	main(int argc, char *argv[])
{
	char	*ductName = (argc > 1 ? argv[1] : NULL);
#endif
	unsigned char		*buffer;
	VOutduct		*vduct;
	PsmAddress		vductElt;
	Sdr			sdr;
	Outduct			duct;
	ClProtocol		protocol;
	Outflow			outflows[3];
	int			i;
	char			*hostName;
	unsigned short		portNbr;
	unsigned int		hostNbr;
	struct sockaddr		socketName;
	struct sockaddr_in	*inetName;
	int			running = 1;
	pthread_mutex_t		mutex;
	KeepaliveThreadParms	parms;
	ReceiveThreadParms	rparms;
	pthread_t		keepaliveThread;
	pthread_t		receiverThread;
	Object			bundleZco;
	BpExtendedCOS		extendedCOS;
	char			destDuctName[MAX_CL_DUCT_NAME_LEN + 1];
	unsigned int		bundleLength;
	int			ductSocket = -1;
	int			bytesSent;
	int 			keepalivePeriod = 0;
	VInduct			*viduct;

	if (ductName == NULL)
	{
		PUTS("Usage: tcpclo <remote host name>[:<port number>]");
		return 0;
	}

	if (bpAttach() < 0)
	{
		putErrmsg("tcpclo can't attach to BP", NULL);
		return 1;
	}

	buffer = MTAKE(TCPCLA_BUFSZ);
	if (buffer == NULL)
	{
		putErrmsg("No memory for TCP buffer in tcpclo.", NULL);
		return 1;
	}

	findOutduct("tcp", ductName, &vduct, &vductElt);
	if (vductElt == 0)
	{
		putErrmsg("No such tcp duct.", ductName);
		MRELEASE(buffer);
		return 1;
	}

	if (vduct->cloPid != ERROR && vduct->cloPid != sm_TaskIdSelf())
	{
		putErrmsg("CLO task is already started for this duct.",
				itoa(vduct->cloPid));
		MRELEASE(buffer);
		return 1;
	}

	/*	All command-line arguments are now validated.		*/

	sdr = getIonsdr();
	CHKERR(sdr_begin_xn(sdr));
	sdr_read(sdr, (char *) &duct, sdr_list_data(sdr, vduct->outductElt),
			sizeof(Outduct));
	sdr_read(sdr, (char *) &protocol, duct.protocol, sizeof(ClProtocol));
	sdr_exit_xn(sdr);
	if (protocol.nominalRate == 0)
	{
		vduct->xmitThrottle.nominalRate = DEFAULT_TCP_RATE;
	}
	else
	{
		vduct->xmitThrottle.nominalRate = protocol.nominalRate;
	}

	memset((char *) outflows, 0, sizeof outflows);
	outflows[0].outboundBundles = duct.bulkQueue;
	outflows[1].outboundBundles = duct.stdQueue;
	outflows[2].outboundBundles = duct.urgentQueue;
	for (i = 0; i < 3; i++)
	{
		outflows[i].svcFactor = 1 << i;
	}

	hostName = ductName;
	parseSocketSpec(ductName, &portNbr, &hostNbr);
	if (portNbr == 0)
	{
		portNbr = BpTcpDefaultPortNbr;
	}

	portNbr = htons(portNbr);
	if (hostNbr == 0)
	{
		putErrmsg("Can't get IP address for host.", hostName);
		MRELEASE(buffer);
		return 1;
	}

	hostNbr = htonl(hostNbr);
	memset((char *) &socketName, 0, sizeof socketName);
	inetName = (struct sockaddr_in *) &socketName;
	inetName->sin_family = AF_INET;
	inetName->sin_port = portNbr;
	memcpy((char *) &(inetName->sin_addr.s_addr), (char *) &hostNbr, 4);
	if (_tcpOutductId(&socketName, "tcp", ductName) < 0)
	{
		putErrmsg("Can't record TCP Outduct ID for connection.", NULL);
		MRELEASE(buffer);
		return -1;
	}

	/*	Set up signal handling.  SIGTERM is shutdown signal.	*/

	oK(tcpcloSemaphore(&(vduct->semaphore)));
	isignal(SIGTERM, shutDownClo);
#ifndef mingw
	isignal(SIGPIPE, handleConnectionLoss);
#endif

	/*	Start the keepalive thread for the eventual connection.	*/
	
	tcpDesiredKeepAlivePeriod = KEEPALIVE_PERIOD;
	parms.cloRunning = &running;
	pthread_mutex_init(&mutex, NULL);
	parms.mutex = &mutex;
	parms.socketName = &socketName;
	parms.ductSocket = &ductSocket;
	parms.keepalivePeriod = &keepalivePeriod;
	if (pthread_begin(&keepaliveThread, NULL, sendKeepalives, &parms))
	{
		putSysErrmsg("tcpclo can't create keepalive thread", NULL);
		MRELEASE(buffer);
		pthread_mutex_destroy(&mutex);
		return 1;
	}

	// Returns the VInduct Object of first induct with same protocol
	// as the outduct. The VInduct is required to create an acq area.
	// The Acq Area inturn uses the throttle information from VInduct
	// object while receiving bundles. The throttle information 
	// of all inducts of the same induct will be the same, so choosing 
	// any induct will serve the purpose.
	
	findVInduct(&viduct,protocol.name);
	if(viduct == NULL)
	{
		putErrmsg("tcpclo can't get VInduct", NULL);
		MRELEASE(buffer);
		pthread_mutex_destroy(&mutex);
		return 1;
	
	}

	rparms.vduct =  viduct;
	rparms.bundleSocket = &ductSocket;
	rparms.mutex = &mutex;
	rparms.cloRunning = &running;
	if (pthread_begin(&receiverThread, NULL, receiveBundles, &rparms))
	{
		putSysErrmsg("tcpclo can't create receive thread", NULL);
		MRELEASE(buffer);
		pthread_mutex_destroy(&mutex);
		return 1;
	}

	/*	Can now begin transmitting to remote duct.		*/

	{
		char	txt[500];

		isprintf(txt, sizeof(txt),
			"[i] tcpclo is running, spec=[%s:%d].", 
			inet_ntoa(inetName->sin_addr),
			ntohs(inetName->sin_port));
		writeMemo(txt);
	}

	while (running && !(sm_SemEnded(tcpcloSemaphore(NULL))))
	{
		if (bpDequeue(vduct, outflows, &bundleZco, &extendedCOS,
				destDuctName, 0, -1) < 0)
		{
			running = 0;	/*	Terminate CLO.		*/
			continue;
		}

		if (bundleZco == 0)	/*	Interrupted.		*/
		{
			continue;
		}

		CHKZERO(sdr_begin_xn(sdr));
		bundleLength = zco_length(sdr, bundleZco);
		sdr_exit_xn(sdr);
		pthread_mutex_lock(&mutex);
		bytesSent = sendBundleByTCPCL(&socketName, &ductSocket,
			bundleLength, bundleZco, buffer, &keepalivePeriod);
		pthread_mutex_unlock(&mutex);
		if(bytesSent < 0)
		{
			running = 0;	/*	Terminate CLO.		*/
		}

		/*	Make sure other tasks have a chance to run.	*/

		sm_TaskYield();
	}
	writeMemo("[i] tcpclo done sending");

	if (sendShutDownMessage(&ductSocket, SHUT_DN_NO, -1, &socketName) < 0)
	{
		putErrmsg("Sending Shutdown message failed!!",NULL);
	}

	if (ductSocket != -1)
	{
		closesocket(ductSocket);
		ductSocket=-1;
	}

	running = 0;
	pthread_join(keepaliveThread, NULL);
	writeMemo("[i] tcpclo keepalive thread killed");

	pthread_join(receiverThread, NULL);
	writeMemo("[i] tcpclo receiver thread killed");

	writeErrmsgMemos();
	writeMemo("[i] tcpclo duct has ended.");
	oK(_tcpOutductId(&socketName, NULL, NULL));
	MRELEASE(buffer);
	pthread_mutex_destroy(&mutex);
	bp_detach();
	return 0;
}
Пример #30
0
static void	*receiveBundles(void *parm)
{
	/*	Main loop for bundle reception thread	*/

	ReceiveThreadParms	*parms = (ReceiveThreadParms *) parm;
	int			threadRunning = 1;
	AcqWorkArea		*work;
	char			*buffer;

	buffer = MTAKE(TCPCLA_BUFSZ);
	if (buffer == NULL)
	{
		putErrmsg("tcpclo receiver can't get TCP buffer", NULL);
		return NULL;
	}

	work = bpGetAcqArea(parms->vduct);
	if (work == NULL)
	{
		putErrmsg("tcpclo receiver can't get acquisition work area",
				NULL);
		MRELEASE(buffer);
		return NULL;
	}

	iblock(SIGTERM);
	while (threadRunning && *(parms->cloRunning))
	{
		if(*(parms->bundleSocket) < 0)
		{
			snooze(1);
			/*Retry later*/
			continue;
		}

		if (bpBeginAcq(work, 0, NULL) < 0)
		{
			putErrmsg("Can't begin acquisition of bundle.", NULL);
			threadRunning = 0;
			continue;
		}
	
		switch (receiveBundleByTcpCL(*(parms->bundleSocket), work,
					buffer))
		{
		case -1:
			putErrmsg("Can't acquire bundle.", NULL);
			pthread_mutex_lock(parms->mutex);
			closesocket(*(parms->bundleSocket));
			*(parms->bundleSocket) = -1;
			pthread_mutex_unlock(parms->mutex);
			continue;

		case 0:			/*	Shutdown message	*/	
			/*	Go back to the start of the while loop	*/
			pthread_mutex_lock(parms->mutex);
			closesocket(*(parms->bundleSocket));
			*(parms->bundleSocket) = -1;
			pthread_mutex_unlock(parms->mutex);			
			continue;

		default:
			break;			/*	Out of switch.	*/
		}

		if (bpEndAcq(work) < 0)
		{
			putErrmsg("Can't end acquisition of bundle.", NULL);
			threadRunning = 0;
		}

		/*	Make sure other tasks have a chance to run.	*/

		sm_TaskYield();
	}

	/*	End of receiver thread; release resources.		*/

	bpReleaseAcqArea(work);
	MRELEASE(buffer);
	return NULL;
}