src/sdo.c
changeset 719 438a979fda5d
parent 717 cfb4f62f35af
parent 712 d1ccff139c17
equal deleted inserted replaced
718:0b33d9cdbdeb 719:438a979fda5d
   121 
   121 
   122 /** Returns the subIndex from the byte 3 of the SDO
   122 /** Returns the subIndex from the byte 3 of the SDO
   123 */
   123 */
   124 #define getSDOsubIndex(byte3) (byte3)
   124 #define getSDOsubIndex(byte3) (byte3)
   125 
   125 
   126 /** Returns the subcommand in SDO block transfert
   126 /** Returns the subcommand in SDO block transfer
   127 */
   127 */
   128 #define getSDOblockSC(byte) (byte & 3)
   128 #define getSDOblockSC(byte) (byte & 3)
   129 
   129 
   130 
   130 
   131 /*!
   131 /*!
   141 	/* Get the client->server cobid.*/
   141 	/* Get the client->server cobid.*/
   142 	offset = d->firstIndex->SDO_CLT;
   142 	offset = d->firstIndex->SDO_CLT;
   143 	if ((offset == 0) || ((offset+d->transfers[id].CliServNbr) > d->lastIndex->SDO_CLT)) {
   143 	if ((offset == 0) || ((offset+d->transfers[id].CliServNbr) > d->lastIndex->SDO_CLT)) {
   144 		return ;
   144 		return ;
   145 	}
   145 	}
   146 	nodeId = *((UNS32*) d->objdict[offset+d->transfers[id].CliServNbr].pSubindex[3].pObject);
   146 	nodeId = (UNS8) *((UNS32*) d->objdict[offset+d->transfers[id].CliServNbr].pSubindex[3].pObject);
   147 	MSG_ERR(0x1A01, "SDO timeout. SDO response not received.", 0);
   147 	MSG_ERR(0x1A01, "SDO timeout. SDO response not received.", 0);
   148 	MSG_WAR(0x2A02, "server node id : ", nodeId);
   148 	MSG_WAR(0x2A02, "server node id : ", nodeId);
   149 	MSG_WAR(0x2A02, "         index : ", d->transfers[id].index);
   149 	MSG_WAR(0x2A02, "         index : ", d->transfers[id].index);
   150 	MSG_WAR(0x2A02, "      subIndex : ", d->transfers[id].subIndex);
   150 	MSG_WAR(0x2A02, "      subIndex : ", d->transfers[id].subIndex);
   151 	/* Reset timer handler */
   151 	/* Reset timer handler */
   186 void resetSDO (CO_Data* d)
   186 void resetSDO (CO_Data* d)
   187 {
   187 {
   188 	UNS8 j;
   188 	UNS8 j;
   189 
   189 
   190 	/* transfer structure initialization */
   190 	/* transfer structure initialization */
   191 	for (j = 0 ; j < SDO_MAX_SIMULTANEOUS_TRANSFERTS ; j++)
   191 	for (j = 0 ; j < SDO_MAX_SIMULTANEOUS_TRANSFERS ; j++)
   192 		resetSDOline(d, j);
   192 		resetSDOline(d, j);
   193 }
   193 }
   194 
   194 
   195 /*!
   195 /*!
   196  **
   196  **
   209 	if( d->transfers[line].count == 0)
   209 	if( d->transfers[line].count == 0)
   210 		d->transfers[line].count = d->transfers[line].offset;
   210 		d->transfers[line].count = d->transfers[line].offset;
   211 	size = d->transfers[line].count;
   211 	size = d->transfers[line].count;
   212 
   212 
   213 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   213 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   214 	if (size > SDO_MAX_LENGTH_TRANSFERT)
   214 	if (size > SDO_MAX_LENGTH_TRANSFER)
   215 	{
   215 	{
   216 		errorCode = setODentry(d, d->transfers[line].index, d->transfers[line].subIndex,
   216 		errorCode = setODentry(d, d->transfers[line].index, d->transfers[line].subIndex,
   217 				(void *) d->transfers[line].dynamicData, &size, 1);
   217 				(void *) d->transfers[line].dynamicData, &size, 1);
   218 	}
   218 	}
   219 	else
   219 	else
   241  **
   241  **
   242  ** @return
   242  ** @return
   243  **/
   243  **/
   244 UNS32 objdictToSDOline (CO_Data* d, UNS8 line)
   244 UNS32 objdictToSDOline (CO_Data* d, UNS8 line)
   245 {
   245 {
   246     UNS32  size = SDO_MAX_LENGTH_TRANSFERT;
   246     UNS32  size = SDO_MAX_LENGTH_TRANSFER;
   247 	UNS8  dataType;
   247 	UNS8  dataType;
   248 	UNS32 errorCode;
   248 	UNS32 errorCode;
   249 
   249 
   250 	MSG_WAR(0x3A05, "objdict->line index : ", d->transfers[line].index);
   250 	MSG_WAR(0x3A05, "objdict->line index : ", d->transfers[line].index);
   251 	MSG_WAR(0x3A06, "  subIndex : ", d->transfers[line].subIndex);
   251 	MSG_WAR(0x3A06, "  subIndex : ", d->transfers[line].subIndex);
   302 UNS8 lineToSDO (CO_Data* d, UNS8 line, UNS32 nbBytes, UNS8* data) {
   302 UNS8 lineToSDO (CO_Data* d, UNS8 line, UNS32 nbBytes, UNS8* data) {
   303 	UNS8 i;
   303 	UNS8 i;
   304 	UNS32 offset;
   304 	UNS32 offset;
   305 
   305 
   306 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   306 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   307 	if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFERT) {
   307 	if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFER) {
   308 		MSG_ERR(0x1A10,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFERT", nbBytes);
   308 		MSG_ERR(0x1A10,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFER", nbBytes);
   309 		return 0xFF;
   309 		return 0xFF;
   310 	}
   310 	}
   311 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   311 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   312 
   312 
   313 	if ((d->transfers[line].offset + nbBytes) > d->transfers[line].count) {
   313 	if ((d->transfers[line].offset + nbBytes) > d->transfers[line].count) {
   314 		MSG_ERR(0x1A11,"SDO Size of data too large. Exceed count", nbBytes);
   314 		MSG_ERR(0x1A11,"SDO Size of data too large. Exceed count", nbBytes);
   315 		return 0xFF;
   315 		return 0xFF;
   316 	}
   316 	}
   317 	offset = d->transfers[line].offset;
   317 	offset = d->transfers[line].offset;
   318 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   318 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   319 	if (d->transfers[line].count <= SDO_MAX_LENGTH_TRANSFERT)
   319 	if (d->transfers[line].count <= SDO_MAX_LENGTH_TRANSFER)
   320 	{
   320 	{
   321 		for (i = 0 ; i < nbBytes ; i++)
   321 		for (i = 0 ; i < nbBytes ; i++)
   322 			* (data + i) = d->transfers[line].data[offset + i];
   322 			* (data + i) = d->transfers[line].data[offset + i];
   323 	}
   323 	}
   324 	else
   324 	else
   352 UNS8 SDOtoLine (CO_Data* d, UNS8 line, UNS32 nbBytes, UNS8* data)
   352 UNS8 SDOtoLine (CO_Data* d, UNS8 line, UNS32 nbBytes, UNS8* data)
   353 {
   353 {
   354 	UNS8 i;
   354 	UNS8 i;
   355 	UNS32 offset;
   355 	UNS32 offset;
   356 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   356 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   357 	if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFERT) {
   357 	if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFER) {
   358 		MSG_ERR(0x1A15,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFERT", nbBytes);
   358 		MSG_ERR(0x1A15,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFER", nbBytes);
   359 		return 0xFF;
   359 		return 0xFF;
   360 	}
   360 	}
   361 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   361 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   362 
   362 
   363 	offset = d->transfers[line].offset;
   363 	offset = d->transfers[line].offset;
   364 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   364 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
   365 	{
   365 	{
   366 		UNS8* lineData = d->transfers[line].data;
   366 		UNS8* lineData = d->transfers[line].data;
   367 		if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFERT) {
   367 		if ((d->transfers[line].offset + nbBytes) > SDO_MAX_LENGTH_TRANSFER) {
   368 			if (d->transfers[line].dynamicData == NULL) {
   368 			if (d->transfers[line].dynamicData == NULL) {
   369 				d->transfers[line].dynamicData = (UNS8*) malloc(SDO_DYNAMIC_BUFFER_ALLOCATION_SIZE);
   369 				d->transfers[line].dynamicData = (UNS8*) malloc(SDO_DYNAMIC_BUFFER_ALLOCATION_SIZE);
   370 				d->transfers[line].dynamicDataSize = SDO_DYNAMIC_BUFFER_ALLOCATION_SIZE;
   370 				d->transfers[line].dynamicDataSize = SDO_DYNAMIC_BUFFER_ALLOCATION_SIZE;
   371 
   371 
   372 				if (d->transfers[line].dynamicData == NULL) {
   372 				if (d->transfers[line].dynamicData == NULL) {
   448 void resetSDOline ( CO_Data* d, UNS8 line )
   448 void resetSDOline ( CO_Data* d, UNS8 line )
   449 {
   449 {
   450 	UNS32 i;
   450 	UNS32 i;
   451 	MSG_WAR(0x3A25, "reset SDO line nb : ", line);
   451 	MSG_WAR(0x3A25, "reset SDO line nb : ", line);
   452 	initSDOline(d, line, 0, 0, 0, SDO_RESET);
   452 	initSDOline(d, line, 0, 0, 0, SDO_RESET);
   453 	for (i = 0 ; i < SDO_MAX_LENGTH_TRANSFERT ; i++)
   453 	for (i = 0 ; i < SDO_MAX_LENGTH_TRANSFER ; i++)
   454 		d->transfers[line].data[i] = 0;
   454 		d->transfers[line].data[i] = 0;
   455 	d->transfers[line].whoami = 0;
   455 	d->transfers[line].whoami = 0;
   456 	d->transfers[line].abortCode = 0;
   456 	d->transfers[line].abortCode = 0;
   457 }
   457 }
   458 
   458 
   514 UNS8 getSDOfreeLine ( CO_Data* d, UNS8 whoami, UNS8 *line )
   514 UNS8 getSDOfreeLine ( CO_Data* d, UNS8 whoami, UNS8 *line )
   515 {
   515 {
   516 
   516 
   517 	UNS8 i;
   517 	UNS8 i;
   518 
   518 
   519 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERTS ; i++){
   519 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERS ; i++){
   520 		if ( d->transfers[i].state == SDO_RESET ) {
   520 		if ( d->transfers[i].state == SDO_RESET ) {
   521 			*line = i;
   521 			*line = i;
   522 			d->transfers[i].whoami = whoami;
   522 			d->transfers[i].whoami = whoami;
   523 			return 0;
   523 			return 0;
   524 		} /* end if */
   524 		} /* end if */
   540 UNS8 getSDOlineOnUse (CO_Data* d, UNS8 CliServNbr, UNS8 whoami, UNS8 *line)
   540 UNS8 getSDOlineOnUse (CO_Data* d, UNS8 CliServNbr, UNS8 whoami, UNS8 *line)
   541 {
   541 {
   542 
   542 
   543 	UNS8 i;
   543 	UNS8 i;
   544 
   544 
   545 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERTS ; i++){
   545 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERS ; i++){
   546 		if ( (d->transfers[i].state != SDO_RESET) &&
   546 		if ( (d->transfers[i].state != SDO_RESET) &&
   547 				(d->transfers[i].state != SDO_ABORTED_INTERNAL) &&
   547 				(d->transfers[i].state != SDO_ABORTED_INTERNAL) &&
   548 				(d->transfers[i].CliServNbr == CliServNbr) &&
   548 				(d->transfers[i].CliServNbr == CliServNbr) &&
   549 				(d->transfers[i].whoami == whoami) ) {
   549 				(d->transfers[i].whoami == whoami) ) {
   550 			if (line) *line = i;
   550 			if (line) *line = i;
   567 UNS8 getSDOlineToClose (CO_Data* d, UNS8 CliServNbr, UNS8 whoami, UNS8 *line)
   567 UNS8 getSDOlineToClose (CO_Data* d, UNS8 CliServNbr, UNS8 whoami, UNS8 *line)
   568 {
   568 {
   569 
   569 
   570 	UNS8 i;
   570 	UNS8 i;
   571 
   571 
   572 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERTS ; i++){
   572 	for (i = 0 ; i < SDO_MAX_SIMULTANEOUS_TRANSFERS ; i++){
   573 		if ( (d->transfers[i].state != SDO_RESET) &&
   573 		if ( (d->transfers[i].state != SDO_RESET) &&
   574 				(d->transfers[i].CliServNbr == CliServNbr) &&
   574 				(d->transfers[i].CliServNbr == CliServNbr) &&
   575 				(d->transfers[i].whoami == whoami) ) {
   575 				(d->transfers[i].whoami == whoami) ) {
   576 			if (line) *line = i;
   576 			if (line) *line = i;
   577 			return 0;
   577 			return 0;
   637  ** @return
   637  ** @return
   638  **/
   638  **/
   639 UNS8 setSDOlineRestBytes (CO_Data* d, UNS8 line, UNS32 nbBytes)
   639 UNS8 setSDOlineRestBytes (CO_Data* d, UNS8 line, UNS32 nbBytes)
   640 {
   640 {
   641 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   641 #ifndef SDO_DYNAMIC_BUFFER_ALLOCATION
   642 	if (nbBytes > SDO_MAX_LENGTH_TRANSFERT) {
   642 	if (nbBytes > SDO_MAX_LENGTH_TRANSFER) {
   643 		MSG_ERR(0x1A35,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFERT", nbBytes);
   643 		MSG_ERR(0x1A35,"SDO Size of data too large. Exceed SDO_MAX_LENGTH_TRANSFER", nbBytes);
   644 		return 0xFF;
   644 		return 0xFF;
   645 	}
   645 	}
   646 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   646 #endif //SDO_DYNAMIC_BUFFER_ALLOCATION
   647 
   647 
   648 	d->transfers[line].count = nbBytes;
   648 	d->transfers[line].count = nbBytes;
   676 		offset = d->firstIndex->SDO_SVR;
   676 		offset = d->firstIndex->SDO_SVR;
   677 		if ((offset == 0) || ((offset+CliServNbr) > d->lastIndex->SDO_SVR)) {
   677 		if ((offset == 0) || ((offset+CliServNbr) > d->lastIndex->SDO_SVR)) {
   678 			MSG_ERR(0x1A42, "SendSDO : SDO server not found", 0);
   678 			MSG_ERR(0x1A42, "SendSDO : SDO server not found", 0);
   679 			return 0xFF;
   679 			return 0xFF;
   680 		}
   680 		}
   681 		m.cob_id = *((UNS32*) d->objdict[offset+CliServNbr].pSubindex[2].pObject);
   681 		m.cob_id = (UNS16) *((UNS32*) d->objdict[offset+CliServNbr].pSubindex[2].pObject);
   682 		MSG_WAR(0x3A41, "I am server Tx cobId : ", m.cob_id);
   682 		MSG_WAR(0x3A41, "I am server Tx cobId : ", m.cob_id);
   683 	}
   683 	}
   684 	else {			/*case client*/
   684 	else {			/*case client*/
   685 		/* Get the client->server cobid.*/
   685 		/* Get the client->server cobid.*/
   686 		offset = d->firstIndex->SDO_CLT;
   686 		offset = d->firstIndex->SDO_CLT;
   687 		if ((offset == 0) || ((offset+CliServNbr) > d->lastIndex->SDO_CLT)) {
   687 		if ((offset == 0) || ((offset+CliServNbr) > d->lastIndex->SDO_CLT)) {
   688 			MSG_ERR(0x1A42, "SendSDO : SDO client not found", 0);
   688 			MSG_ERR(0x1A42, "SendSDO : SDO client not found", 0);
   689 			return 0xFF;
   689 			return 0xFF;
   690 		}
   690 		}
   691 		m.cob_id = *((UNS32*) d->objdict[offset+CliServNbr].pSubindex[1].pObject);
   691 		m.cob_id = (UNS16) *((UNS32*) d->objdict[offset+CliServNbr].pSubindex[1].pObject);
   692 		MSG_WAR(0x3A41, "I am client Tx cobId : ", m.cob_id);
   692 		MSG_WAR(0x3A41, "I am client Tx cobId : ", m.cob_id);
   693 	}
   693 	}
   694 	/* message copy for sending */
   694 	/* message copy for sending */
   695 	m.rtr = NOT_A_REQUEST;
   695 	m.rtr = NOT_A_REQUEST;
   696 	/* the length of SDO must be 8 */
   696 	/* the length of SDO must be 8 */
   759 	UNS32 i;
   759 	UNS32 i;
   760 	UNS8	j;
   760 	UNS8	j;
   761 	UNS32 *pCobId = NULL;
   761 	UNS32 *pCobId = NULL;
   762 	UNS16 offset;
   762 	UNS16 offset;
   763 	UNS16 lastIndex;
   763 	UNS16 lastIndex;
   764 	UNS8 SubCommand;	/* Block transfert only */
   764 	UNS8 SubCommand;	/* Block transfer only */
   765     UNS8 SeqNo;         /* Sequence number in block transfert */
   765     UNS8 SeqNo;         /* Sequence number in block transfer */
   766     UNS8 AckSeq;        /* Sequence number of last segment that was received successfully */
   766     UNS8 AckSeq;        /* Sequence number of last segment that was received successfully */
   767 	UNS8 NbBytesNoData; /* Number of bytes that do not contain data in last segment of block transfert */ 
   767 	UNS8 NbBytesNoData; /* Number of bytes that do not contain data in last segment of block transfer */ 
   768 
   768 
   769 	MSG_WAR(0x3A60, "proceedSDO ", 0);
   769 	MSG_WAR(0x3A60, "proceedSDO ", 0);
   770 	whoami = SDO_UNKNOWN;
   770 	whoami = SDO_UNKNOWN;
   771 	/* Looking for the cobId in the object dictionary. */
   771 	/* Looking for the cobId in the object dictionary. */
   772 	/* Am-I a server ? */
   772 	/* Am-I a server ? */
   831 	}
   831 	}
   832 	else {
   832 	else {
   833 		MSG_WAR(0x3A69, "I am SERVER number ", CliServNbr);
   833 		MSG_WAR(0x3A69, "I am SERVER number ", CliServNbr);
   834 	}
   834 	}
   835 
   835 
   836 	/* Look for an SDO transfert already initiated. */
   836 	/* Look for an SDO transfer already initiated. */
   837 	err = getSDOlineOnUse( d, CliServNbr, whoami, &line );
   837 	err = getSDOlineOnUse( d, CliServNbr, whoami, &line );
   838 
   838 
   839 	/* Let's find cs value, first it is set as "not valid" */
   839 	/* Let's find cs value, first it is set as "not valid" */
   840 	cs = 0xFF; 
   840 	cs = 0xFF; 
   841 	/* Special cases for block transfert : in frames with segment data cs is not spécified */
   841 	/* Special cases for block transfer : in frames with segment data cs is not spécified */
   842    	if (!err) {
   842    	if (!err) {
   843 		if ((whoami == SDO_SERVER) && (d->transfers[line].state == SDO_BLOCK_DOWNLOAD_IN_PROGRESS) ||
   843 		if ((whoami == SDO_SERVER) && (d->transfers[line].state == SDO_BLOCK_DOWNLOAD_IN_PROGRESS) ||
   844 			(whoami == SDO_CLIENT) && (d->transfers[line].state == SDO_BLOCK_UPLOAD_IN_PROGRESS)) {		
   844 			(whoami == SDO_CLIENT) && (d->transfers[line].state == SDO_BLOCK_UPLOAD_IN_PROGRESS)) {		
   845 			if(m->data[0] == 0x80)	/* If first byte is 0x80 it is an abort frame (seqno = 0 not allowed) */
   845 			if(m->data[0] == 0x80)	/* If first byte is 0x80 it is an abort frame (seqno = 0 not allowed) */
   846 				cs = 4;
   846 				cs = 4;
   858 	switch (cs) {
   858 	switch (cs) {
   859 
   859 
   860 		case 0:
   860 		case 0:
   861 			/* I am SERVER */
   861 			/* I am SERVER */
   862 			if (whoami == SDO_SERVER) {
   862 			if (whoami == SDO_SERVER) {
   863 				/* Receiving a download segment data : an SDO transfert should have been yet initiated. */
   863 				/* Receiving a download segment data : an SDO transfer should have been yet initiated. */
   864 				if (!err)
   864 				if (!err)
   865 					err = d->transfers[line].state != SDO_DOWNLOAD_IN_PROGRESS;
   865 					err = d->transfers[line].state != SDO_DOWNLOAD_IN_PROGRESS;
   866 				if (err) {
   866 				if (err) {
   867 					MSG_ERR(0x1A70, "SDO error : Received download segment for unstarted trans. index 0x1200 + ",
   867 					MSG_ERR(0x1A70, "SDO error : Received download segment for unstarted trans. index 0x1200 + ",
   868 							CliServNbr);
   868 							CliServNbr);
   880 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_TOGGLE_NOT_ALTERNED);
   880 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_TOGGLE_NOT_ALTERNED);
   881 					return 0xFF;
   881 					return 0xFF;
   882 				}
   882 				}
   883 				/* Nb of data to be downloaded */
   883 				/* Nb of data to be downloaded */
   884 				nbBytes = 7 - getSDOn3(m->data[0]);
   884 				nbBytes = 7 - getSDOn3(m->data[0]);
   885 				/* Store the data in the transfert structure. */
   885 				/* Store the data in the transfer structure. */
   886 				err = SDOtoLine(d, line, nbBytes, (*m).data + 1);
   886 				err = SDOtoLine(d, line, nbBytes, (*m).data + 1);
   887 				if (err) {
   887 				if (err) {
   888 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
   888 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
   889 					return 0xFF;
   889 					return 0xFF;
   890 				}
   890 				}
   971 				MSG_WAR(0x3A79, "Received SDO Initiate Download (to store data) defined at index 0x1200 + ",
   971 				MSG_WAR(0x3A79, "Received SDO Initiate Download (to store data) defined at index 0x1200 + ",
   972 						CliServNbr);
   972 						CliServNbr);
   973 				MSG_WAR(0x3A80, "Writing at index : ", index);
   973 				MSG_WAR(0x3A80, "Writing at index : ", index);
   974 				MSG_WAR(0x3A80, "Writing at subIndex : ", subIndex);
   974 				MSG_WAR(0x3A80, "Writing at subIndex : ", subIndex);
   975 
   975 
   976 				/* Search if a SDO transfert have been yet initiated */
   976 				/* Search if a SDO transfer have been yet initiated */
   977 				if (! err) {
   977 				if (! err) {
   978 					MSG_ERR(0x1A81, "SDO error : Transmission yet started.", 0);
   978 					MSG_ERR(0x1A81, "SDO error : Transmission yet started.", 0);
   979 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
   979 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
   980 					return 0xFF;
   980 					return 0xFF;
   981 				}
   981 				}
   999 					if (err) {
   999 					if (err) {
  1000 						failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1000 						failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1001 						return 0xFF;
  1001 						return 0xFF;
  1002 					}
  1002 					}
  1003 
  1003 
  1004 					/* SDO expedited -> transfert finished. Data can be stored in the dictionary. */
  1004 					/* SDO expedited -> transfer finished. Data can be stored in the dictionary. */
  1005 					/*The line will be reseted when it is downloading in the dictionary. */
  1005 					/*The line will be reseted when it is downloading in the dictionary. */
  1006 					MSG_WAR(0x3A83, "SDO Initiate Download is an expedited transfert. Finished. ", 0);
  1006 					MSG_WAR(0x3A83, "SDO Initiate Download is an expedited transfer. Finished. ", 0);
  1007 					/* Transfering line data to object dictionary. */
  1007 					/* Transfering line data to object dictionary. */
  1008 					errorCode = SDOlineToObjdict(d, line);
  1008 					errorCode = SDOlineToObjdict(d, line);
  1009 					if (errorCode) {
  1009 					if (errorCode) {
  1010 						MSG_ERR(0x1A84, "SDO error : Unable to copy the data in the object dictionary", 0);
  1010 						MSG_ERR(0x1A84, "SDO error : Unable to copy the data in the object dictionary", 0);
  1011 						failedSDO(d, CliServNbr, whoami, index, subIndex, errorCode);
  1011 						failedSDO(d, CliServNbr, whoami, index, subIndex, errorCode);
  1012 						return 0xFF;
  1012 						return 0xFF;
  1013 					}
  1013 					}
  1014 					/* Release of the line. */
  1014 					/* Release of the line. */
  1015 					resetSDOline(d, line);
  1015 					resetSDOline(d, line);
  1016 				}
  1016 				}
  1017 				else {/* So, if it is not an expedited transfert */
  1017 				else {/* So, if it is not an expedited transfer */
  1018 					if (getSDOs(m->data[0])) {
  1018 					if (getSDOs(m->data[0])) {
  1019 						nbBytes = (m->data[4]) + ((UNS32)(m->data[5])<<8) + ((UNS32)(m->data[6])<<16) + ((UNS32)(m->data[7])<<24);
  1019 						nbBytes = (m->data[4]) + ((UNS32)(m->data[5])<<8) + ((UNS32)(m->data[6])<<16) + ((UNS32)(m->data[7])<<24);
  1020 						err = setSDOlineRestBytes(d, CliServNbr, nbBytes);
  1020 						err = setSDOlineRestBytes(d, line, nbBytes);
  1021 						if (err) {
  1021 						if (err) {
  1022 							failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1022 							failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1023 							return 0xFF;
  1023 							return 0xFF;
  1024 						}
  1024 						}
  1025 					}
  1025 					}
  1101 				subIndex = getSDOsubIndex(m->data[3]);
  1101 				subIndex = getSDOsubIndex(m->data[3]);
  1102 				MSG_WAR(0x3A89, "Received SDO Initiate upload (to send data) defined at index 0x1200 + ",
  1102 				MSG_WAR(0x3A89, "Received SDO Initiate upload (to send data) defined at index 0x1200 + ",
  1103 						CliServNbr);
  1103 						CliServNbr);
  1104 				MSG_WAR(0x3A90, "Reading at index : ", index);
  1104 				MSG_WAR(0x3A90, "Reading at index : ", index);
  1105 				MSG_WAR(0x3A91, "Reading at subIndex : ", subIndex);
  1105 				MSG_WAR(0x3A91, "Reading at subIndex : ", subIndex);
  1106 				/* Search if a SDO transfert have been yet initiated*/
  1106 				/* Search if a SDO transfer have been yet initiated*/
  1107 				if (! err) {
  1107 				if (! err) {
  1108 					MSG_ERR(0x1A92, "SDO error : Transmission yet started at line : ", line);
  1108 					MSG_ERR(0x1A92, "SDO error : Transmission yet started at line : ", line);
  1109 					MSG_WAR(0x3A93, "Server Nbr = ", CliServNbr);
  1109 					MSG_WAR(0x3A93, "Server Nbr = ", CliServNbr);
  1110 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
  1110 					failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
  1111 					return 0xFF;
  1111 					return 0xFF;
  1129 					return 0xFF;
  1129 					return 0xFF;
  1130 				}
  1130 				}
  1131 				/* Preparing the response.*/
  1131 				/* Preparing the response.*/
  1132 				getSDOlineRestBytes(d, line, &nbBytes);	/* Nb bytes to transfer ? */
  1132 				getSDOlineRestBytes(d, line, &nbBytes);	/* Nb bytes to transfer ? */
  1133 				if (nbBytes > 4) {
  1133 				if (nbBytes > 4) {
  1134 					/* normal transfert. (segmented). */
  1134 					/* normal transfer. (segmented). */
  1135 					/* code to send the initiate upload response. (cs = 2) */
  1135 					/* code to send the initiate upload response. (cs = 2) */
  1136 					data[0] = (2 << 5) | 1;
  1136 					data[0] = (2 << 5) | 1;
  1137 					data[1] = index & 0xFF;        /* LSB */
  1137 					data[1] = index & 0xFF;        /* LSB */
  1138 					data[2] = (index >> 8) & 0xFF; /* MSB */
  1138 					data[2] = (index >> 8) & 0xFF; /* MSB */
  1139 					data[3] = subIndex;
  1139 					data[3] = subIndex;
  1140 					data[4] = nbBytes; 
  1140 					data[4] = (UNS8) nbBytes;
  1141 					data[5] = nbBytes >> 8; 
  1141 					data[5] = (UNS8) (nbBytes >> 8);
  1142 					data[6] = nbBytes >> 16; 
  1142 					data[6] = (UNS8) (nbBytes >> 16);
  1143 					data[7] = nbBytes >> 24; 
  1143 					data[7] = (UNS8) (nbBytes >> 24);
  1144  					MSG_WAR(0x3A95, "SDO. Sending normal upload initiate response defined at index 0x1200 + ", nodeId);
  1144  					MSG_WAR(0x3A95, "SDO. Sending normal upload initiate response defined at index 0x1200 + ", nodeId);
  1145 					sendSDO(d, whoami, CliServNbr, data);
  1145 					sendSDO(d, whoami, CliServNbr, data);
  1146 				}
  1146 				}
  1147 				else {
  1147 				else {
  1148 					/* Expedited upload. (cs = 2 ; e = 1) */
  1148 					/* Expedited upload. (cs = 2 ; e = 1) */
  1187 					err = SDOtoLine(d, line, nbBytes, (*m).data + 4);
  1187 					err = SDOtoLine(d, line, nbBytes, (*m).data + 4);
  1188 					if (err) {
  1188 					if (err) {
  1189 						failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1189 						failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_GENERAL_ERROR);
  1190 						return 0xFF;
  1190 						return 0xFF;
  1191 					}
  1191 					}
  1192 					/* SDO expedited -> transfert finished. data are available via  getReadResultNetworkDict(). */
  1192 					/* SDO expedited -> transfer finished. data are available via  getReadResultNetworkDict(). */
  1193 					MSG_WAR(0x3A98, "SDO expedited upload finished. Response received from node : ", nodeId);
  1193 					MSG_WAR(0x3A98, "SDO expedited upload finished. Response received from node : ", nodeId);
  1194 					StopSDO_TIMER(line)
  1194 					StopSDO_TIMER(line)
  1195 						d->transfers[line].count = nbBytes;
  1195 						d->transfers[line].count = nbBytes;
  1196 					d->transfers[line].state = SDO_FINISHED;
  1196 					d->transfers[line].state = SDO_FINISHED;
  1197 					if(d->transfers[line].Callback) (*d->transfers[line].Callback)(d,nodeId);
  1197 					if(d->transfers[line].Callback) (*d->transfers[line].Callback)(d,nodeId);
  1198 					return 0;
  1198 					return 0;
  1199 				}
  1199 				}
  1200 				else { /* So, if it is not an expedited transfert */
  1200 				else { /* So, if it is not an expedited transfer */
  1201 					/* Storing the nb of data to receive. */
  1201 					/* Storing the nb of data to receive. */
  1202 					if (getSDOs(m->data[0])) {
  1202 					if (getSDOs(m->data[0])) {
  1203 						nbBytes = m->data[4] + ((UNS32)(m->data[5])<<8) + ((UNS32)(m->data[6])<<16) + ((UNS32)(m->data[7])<<24);
  1203 						nbBytes = m->data[4] + ((UNS32)(m->data[5])<<8) + ((UNS32)(m->data[6])<<16) + ((UNS32)(m->data[7])<<24);
  1204 						err = setSDOlineRestBytes(d, line, nbBytes);
  1204 						err = setSDOlineRestBytes(d, line, nbBytes);
  1205 						if (err) {
  1205 						if (err) {
  1219 
  1219 
  1220 		case 3:
  1220 		case 3:
  1221 			/* I am SERVER */
  1221 			/* I am SERVER */
  1222 			if (whoami == SDO_SERVER) {
  1222 			if (whoami == SDO_SERVER) {
  1223 				/* Receiving a upload segment. */
  1223 				/* Receiving a upload segment. */
  1224 				/* A SDO transfert should have been yet initiated. */
  1224 				/* A SDO transfer should have been yet initiated. */
  1225 				if (!err)
  1225 				if (!err)
  1226 					err = d->transfers[line].state != SDO_UPLOAD_IN_PROGRESS;
  1226 					err = d->transfers[line].state != SDO_UPLOAD_IN_PROGRESS;
  1227 				if (err) {
  1227 				if (err) {
  1228 					MSG_ERR(0x1AA0, "SDO error : Received upload segment for unstarted trans. index 0x1200 + ",
  1228 					MSG_ERR(0x1AA0, "SDO error : Received upload segment for unstarted trans. index 0x1200 + ",
  1229 							CliServNbr);
  1229 							CliServNbr);
  1364 				    subIndex = getSDOsubIndex(m->data[3]);
  1364 				    subIndex = getSDOsubIndex(m->data[3]);
  1365 				    MSG_WAR(0x3AB2, "Received SDO Initiate block upload defined at index 0x1200 + ",
  1365 				    MSG_WAR(0x3AB2, "Received SDO Initiate block upload defined at index 0x1200 + ",
  1366 						CliServNbr);
  1366 						CliServNbr);
  1367 				    MSG_WAR(0x3AB3, "Reading at index : ", index);
  1367 				    MSG_WAR(0x3AB3, "Reading at index : ", index);
  1368 				    MSG_WAR(0x3AB4, "Reading at subIndex : ", subIndex);
  1368 				    MSG_WAR(0x3AB4, "Reading at subIndex : ", subIndex);
  1369 				    /* Search if a SDO transfert have been yet initiated */
  1369 				    /* Search if a SDO transfer have been yet initiated */
  1370 				    if (! err) {
  1370 				    if (! err) {
  1371 					    MSG_ERR(0x1A93, "SDO error : Transmission yet started at line : ", line);
  1371 					    MSG_ERR(0x1A93, "SDO error : Transmission yet started at line : ", line);
  1372 					    MSG_WAR(0x3AB5, "Server Nbr = ", CliServNbr);
  1372 					    MSG_WAR(0x3AB5, "Server Nbr = ", CliServNbr);
  1373 					    failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
  1373 					    failedSDO(d, CliServNbr, whoami, index, subIndex, SDOABT_LOCAL_CTRL_ERROR);
  1374 					    return 0xFF;
  1374 					    return 0xFF;
  1397                     d->transfers[line].objsize = nbBytes;
  1397                     d->transfers[line].objsize = nbBytes;
  1398                     data[0] = (6 << 5) | (1 << 1) | SDO_BSS_INITIATE_UPLOAD_RESPONSE;
  1398                     data[0] = (6 << 5) | (1 << 1) | SDO_BSS_INITIATE_UPLOAD_RESPONSE;
  1399 					data[1] = index & 0xFF;        /* LSB */
  1399 					data[1] = index & 0xFF;        /* LSB */
  1400 					data[2] = (index >> 8) & 0xFF; /* MSB */
  1400 					data[2] = (index >> 8) & 0xFF; /* MSB */
  1401 					data[3] = subIndex;
  1401 					data[3] = subIndex;
  1402 					data[4] = nbBytes;
  1402 					data[4] = (UNS8) nbBytes;
  1403 					data[5] = nbBytes >> 8;
  1403 					data[5] = (UNS8) (nbBytes >> 8);
  1404 					data[6] = nbBytes >> 16;
  1404 					data[6] = (UNS8) (nbBytes >> 16);
  1405 					data[7] = nbBytes >> 24;
  1405 					data[7] = (UNS8) (nbBytes >> 24);
  1406 					MSG_WAR(0x3A9A, "SDO. Sending normal block upload initiate response defined at index 0x1200 + ", nodeId);
  1406 					MSG_WAR(0x3A9A, "SDO. Sending normal block upload initiate response defined at index 0x1200 + ", nodeId);
  1407 					sendSDO(d, whoami, CliServNbr, data);
  1407 					sendSDO(d, whoami, CliServNbr, data);
  1408                 }
  1408                 }
  1409 				else if (SubCommand == SDO_BCS_END_UPLOAD_REQUEST) {
  1409 				else if (SubCommand == SDO_BCS_END_UPLOAD_REQUEST) {
  1410 				    MSG_WAR(0x3AA2, "Received SDO block END upload request defined at index 0x1200 + ", CliServNbr);
  1410 				    MSG_WAR(0x3AA2, "Received SDO block END upload request defined at index 0x1200 + ", CliServNbr);
  1411  				    /* A SDO transfert should have been yet initiated. */
  1411  				    /* A SDO transfer should have been yet initiated. */
  1412 				    if (!err)
  1412 				    if (!err)
  1413 					    err = d->transfers[line].state != SDO_BLOCK_UPLOAD_IN_PROGRESS;
  1413 					    err = d->transfers[line].state != SDO_BLOCK_UPLOAD_IN_PROGRESS;
  1414 				    if (err) {
  1414 				    if (err) {
  1415 					    MSG_ERR(0x1AA1, "SDO error : Received block upload request for unstarted trans. index 0x1200 + ",
  1415 					    MSG_ERR(0x1AA1, "SDO error : Received block upload request for unstarted trans. index 0x1200 + ",
  1416 							    CliServNbr);
  1416 							    CliServNbr);
  1419 				    }
  1419 				    }
  1420                     /* Release the line */
  1420                     /* Release the line */
  1421 					resetSDOline(d, line);
  1421 					resetSDOline(d, line);
  1422                 }
  1422                 }
  1423 				else if ((SubCommand == SDO_BCS_UPLOAD_RESPONSE) || (SubCommand == SDO_BCS_START_UPLOAD)) {
  1423 				else if ((SubCommand == SDO_BCS_UPLOAD_RESPONSE) || (SubCommand == SDO_BCS_START_UPLOAD)) {
  1424  				    /* A SDO transfert should have been yet initiated. */
  1424  				    /* A SDO transfer should have been yet initiated. */
  1425 				    if (!err)
  1425 				    if (!err)
  1426 					    err = d->transfers[line].state != SDO_BLOCK_UPLOAD_IN_PROGRESS;
  1426 					    err = d->transfers[line].state != SDO_BLOCK_UPLOAD_IN_PROGRESS;
  1427 				    if (err) {
  1427 				    if (err) {
  1428 					    MSG_ERR(0x1AA1, "SDO error : Received block upload response for unstarted trans. index 0x1200 + ",
  1428 					    MSG_ERR(0x1AA1, "SDO error : Received block upload response for unstarted trans. index 0x1200 + ",
  1429 							    CliServNbr);
  1429 							    CliServNbr);
  1457 					        return 0xFF;
  1457 					        return 0xFF;
  1458                         }
  1458                         }
  1459            			}
  1459            			}
  1460                     else
  1460                     else
  1461 					    MSG_WAR(0x3AA2, "Received SDO block START upload defined at index 0x1200 + ", CliServNbr);
  1461 					    MSG_WAR(0x3AA2, "Received SDO block START upload defined at index 0x1200 + ", CliServNbr);
  1462                     d->transfers[line].lastblockoffset = d->transfers[line].offset;
  1462                     d->transfers[line].lastblockoffset = (UNS8) d->transfers[line].offset;
  1463                     for(SeqNo = 1 ; SeqNo <= d->transfers[line].blksize ; SeqNo++) {
  1463                     for(SeqNo = 1 ; SeqNo <= d->transfers[line].blksize ; SeqNo++) {
  1464                         d->transfers[line].seqno = SeqNo;
  1464                         d->transfers[line].seqno = SeqNo;
  1465 				        getSDOlineRestBytes(d, line, &nbBytes);
  1465 				        getSDOlineRestBytes(d, line, &nbBytes);
  1466                         if (nbBytes > 7) {
  1466                         if (nbBytes > 7) {
  1467 					        /* The segment to transfer is not the last one.*/
  1467 					        /* The segment to transfer is not the last one.*/
  1484 					        }
  1484 					        }
  1485 					        for (i = nbBytes + 1 ; i < 8 ; i++)
  1485 					        for (i = nbBytes + 1 ; i < 8 ; i++)
  1486 						        data[i] = 0;
  1486 						        data[i] = 0;
  1487 					        MSG_WAR(0x3AA5, "SDO. Sending last upload segment defined at index 0x1200 + ", CliServNbr);
  1487 					        MSG_WAR(0x3AA5, "SDO. Sending last upload segment defined at index 0x1200 + ", CliServNbr);
  1488 					        sendSDO(d, whoami, CliServNbr, data);
  1488 					        sendSDO(d, whoami, CliServNbr, data);
  1489                             d->transfers[line].endfield = 7 - nbBytes;
  1489                             d->transfers[line].endfield = (UNS8) (7 - nbBytes);
  1490                             break;
  1490                             break;
  1491 				        }
  1491 				        }
  1492                     }
  1492                     }
  1493                 }
  1493                 }
  1494 			}      /* end if SERVER */
  1494 			}      /* end if SERVER */
  1529 							    CliServNbr);
  1529 							    CliServNbr);
  1530 					        failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1530 					        failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1531 					        return 0xFF;
  1531 					        return 0xFF;
  1532                         }
  1532                         }
  1533 					}
  1533 					}
  1534                  	d->transfers[line].lastblockoffset = d->transfers[line].offset;
  1534                  	d->transfers[line].lastblockoffset = (UNS8) d->transfers[line].offset;
  1535                 	for(SeqNo = 1 ; SeqNo <= d->transfers[line].blksize ; SeqNo++) {
  1535                 	for(SeqNo = 1 ; SeqNo <= d->transfers[line].blksize ; SeqNo++) {
  1536                         d->transfers[line].seqno = SeqNo;
  1536                         d->transfers[line].seqno = SeqNo;
  1537 				        getSDOlineRestBytes(d, line, &nbBytes);
  1537 				        getSDOlineRestBytes(d, line, &nbBytes);
  1538                         if (nbBytes > 7) {
  1538                         if (nbBytes > 7) {
  1539 					        /* The segment to transfer is not the last one.*/
  1539 					        /* The segment to transfer is not the last one.*/
  1556 					        }
  1556 					        }
  1557 					        for (i = nbBytes + 1 ; i < 8 ; i++)
  1557 					        for (i = nbBytes + 1 ; i < 8 ; i++)
  1558 						        data[i] = 0;
  1558 						        data[i] = 0;
  1559 					        MSG_WAR(0x3AAB, "SDO. Sending last download segment to node id ", nodeId);
  1559 					        MSG_WAR(0x3AAB, "SDO. Sending last download segment to node id ", nodeId);
  1560 					        sendSDO(d, whoami, CliServNbr, data);
  1560 					        sendSDO(d, whoami, CliServNbr, data);
  1561                             d->transfers[line].endfield = 7 - nbBytes;
  1561                             d->transfers[line].endfield = (UNS8) (7 - nbBytes);
  1562                             break;
  1562                             break;
  1563 				        }
  1563 				        }
  1564                     }
  1564                     }
  1565 				}
  1565 				}
  1566 				else if (SubCommand == SDO_BSS_END_DOWNLOAD_RESPONSE) {
  1566 				else if (SubCommand == SDO_BSS_END_DOWNLOAD_RESPONSE) {
  1604                     d->transfers[line].rxstep = RXSTEP_STARTED;
  1604                     d->transfers[line].rxstep = RXSTEP_STARTED;
  1605                     d->transfers[line].peerCRCsupport = ((m->data[0])>>2) & 1;
  1605                     d->transfers[line].peerCRCsupport = ((m->data[0])>>2) & 1;
  1606 					if ((m->data[0]) & 2)	/* if data set size is indicated */
  1606 					if ((m->data[0]) & 2)	/* if data set size is indicated */
  1607                     	d->transfers[line].objsize = (UNS32)m->data[4] + (UNS32)m->data[5]*256 + (UNS32)m->data[6]*256*256 + (UNS32)m->data[7]*256*256*256;
  1607                     	d->transfers[line].objsize = (UNS32)m->data[4] + (UNS32)m->data[5]*256 + (UNS32)m->data[6]*256*256 + (UNS32)m->data[7]*256*256*256;
  1608                     data[0] = (5 << 5) | SDO_BSS_INITIATE_DOWNLOAD_RESPONSE;
  1608                     data[0] = (5 << 5) | SDO_BSS_INITIATE_DOWNLOAD_RESPONSE;
  1609 					data[1] = index;        /* LSB */
  1609 					data[1] = (UNS8) index;        /* LSB */
  1610 					data[2] = index >> 8;   /* MSB */
  1610 					data[2] = (UNS8) (index >> 8); /* MSB */
  1611 					data[3] = subIndex;
  1611 					data[3] = subIndex;
  1612 					data[4] = SDO_BLOCK_SIZE;
  1612 					data[4] = SDO_BLOCK_SIZE;
  1613 					data[5] = data[6] = data[7] = 0;
  1613 					data[5] = data[6] = data[7] = 0;
  1614 					MSG_WAR(0x3AAD, "SDO. Sending block download initiate response - index 0x1200 + ", CliServNbr);
  1614 					MSG_WAR(0x3AAD, "SDO. Sending block download initiate response - index 0x1200 + ", CliServNbr);
  1615 					sendSDO(d, whoami, CliServNbr, data);
  1615 					sendSDO(d, whoami, CliServNbr, data);
  1634                         d->transfers[line].seqno = 0;
  1634                         d->transfers[line].seqno = 0;
  1635 					}
  1635 					}
  1636 					else {
  1636 					else {
  1637 					   	if (SeqNo == (d->transfers[line].seqno + 1)) {	
  1637 					   	if (SeqNo == (d->transfers[line].seqno + 1)) {	
  1638 							d->transfers[line].seqno = SeqNo;
  1638 							d->transfers[line].seqno = SeqNo;
  1639 							/* Store the data in the transfert structure. */
  1639 							/* Store the data in the transfer structure. */
  1640 							err = SDOtoLine(d, line, 7, (*m).data + 1);
  1640 							err = SDOtoLine(d, line, 7, (*m).data + 1);
  1641 							if (err) {
  1641 							if (err) {
  1642 								failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1642 								failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1643 								return 0xFF;
  1643 								return 0xFF;
  1644 							}
  1644 							}
  1662     					failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1662     					failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1663 	    				return 0xFF;
  1663 	    				return 0xFF;
  1664 					}
  1664 					}
  1665     		    	RestartSDO_TIMER(line)
  1665     		    	RestartSDO_TIMER(line)
  1666 					NbBytesNoData = (m->data[0]>>2) & 0x07;
  1666 					NbBytesNoData = (m->data[0]>>2) & 0x07;
  1667 					/* Store the data in the transfert structure. */
  1667 					/* Store the data in the transfer structure. */
  1668 					err = SDOtoLine(d, line, 7-NbBytesNoData, d->transfers[line].tmpData + 1);
  1668 					err = SDOtoLine(d, line, 7-NbBytesNoData, d->transfers[line].tmpData + 1);
  1669 					if (err) {
  1669 					if (err) {
  1670 						failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1670 						failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1671 						return 0xFF;
  1671 						return 0xFF;
  1672 					}
  1672 					}
  1734                         d->transfers[line].seqno = 0;
  1734                         d->transfers[line].seqno = 0;
  1735 					}
  1735 					}
  1736 					else {
  1736 					else {
  1737 					   	if (SeqNo == (d->transfers[line].seqno + 1)) {	
  1737 					   	if (SeqNo == (d->transfers[line].seqno + 1)) {	
  1738 							d->transfers[line].seqno = SeqNo;
  1738 							d->transfers[line].seqno = SeqNo;
  1739 							/* Store the data in the transfert structure. */
  1739 							/* Store the data in the transfer structure. */
  1740 							err = SDOtoLine(d, line, 7, (*m).data + 1);
  1740 							err = SDOtoLine(d, line, 7, (*m).data + 1);
  1741 							if (err) {
  1741 							if (err) {
  1742 								failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1742 								failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1743 								return 0xFF;
  1743 								return 0xFF;
  1744 							}
  1744 							}
  1760 			    		MSG_ERR(0x1AAD, "SDO error block upload : Received wrong subcommand from node id ", nodeId);
  1760 			    		MSG_ERR(0x1AAD, "SDO error block upload : Received wrong subcommand from node id ", nodeId);
  1761     					failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1761     					failedSDO(d, CliServNbr, whoami, 0, 0, SDOABT_LOCAL_CTRL_ERROR);
  1762 	    				return 0xFF;
  1762 	    				return 0xFF;
  1763 					}
  1763 					}
  1764 					NbBytesNoData = (m->data[0]>>2) & 0x07;
  1764 					NbBytesNoData = (m->data[0]>>2) & 0x07;
  1765 					/* Store the data in the transfert structure. */
  1765 					/* Store the data in the transfer structure. */
  1766 					err = SDOtoLine(d, line, 7-NbBytesNoData, d->transfers[line].tmpData + 1);
  1766 					err = SDOtoLine(d, line, 7-NbBytesNoData, d->transfers[line].tmpData + 1);
  1767 					if (err) {
  1767 					if (err) {
  1768 						failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1768 						failedSDO(d, CliServNbr, whoami, d->transfers[line].index,  d->transfers[line].subIndex, SDOABT_GENERAL_ERROR);
  1769 						return 0xFF;
  1769 						return 0xFF;
  1770 					}
  1770 					}
  1907 	d->transfers[line].count = count;
  1907 	d->transfers[line].count = count;
  1908 	d->transfers[line].dataType = dataType;
  1908 	d->transfers[line].dataType = dataType;
  1909 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
  1909 #ifdef SDO_DYNAMIC_BUFFER_ALLOCATION
  1910 	{
  1910 	{
  1911 		UNS8* lineData = d->transfers[line].data;
  1911 		UNS8* lineData = d->transfers[line].data;
  1912 		if (count > SDO_MAX_LENGTH_TRANSFERT)
  1912 		if (count > SDO_MAX_LENGTH_TRANSFER)
  1913 		{
  1913 		{
  1914 			d->transfers[line].dynamicData = (UNS8*) malloc(count);
  1914 			d->transfers[line].dynamicData = (UNS8*) malloc(count);
  1915 			d->transfers[line].dynamicDataSize = count;
  1915 			d->transfers[line].dynamicDataSize = count;
  1916 			if (d->transfers[line].dynamicData == NULL)
  1916 			if (d->transfers[line].dynamicData == NULL)
  1917 			{
  1917 			{
  1950  	    for (i = 0 ; i < 4 ; i++)
  1950  	    for (i = 0 ; i < 4 ; i++)
  1951 		    buf[i+4] = (UNS8)((count >> (i<<3))); /* i*8 */
  1951 		    buf[i+4] = (UNS8)((count >> (i<<3))); /* i*8 */
  1952     }
  1952     }
  1953     else {
  1953     else {
  1954 	    /* Send the SDO to the server. Initiate download, cs=1. */
  1954 	    /* Send the SDO to the server. Initiate download, cs=1. */
  1955 	    if (count <= 4) { /* Expedited transfert */
  1955 	    if (count <= 4) { /* Expedited transfer */
  1956 		    buf[0] = (UNS8)((1 << 5) | ((4 - count) << 2) | 3);
  1956 		    buf[0] = (UNS8)((1 << 5) | ((4 - count) << 2) | 3);
  1957 		    for (i = 4 ; i < 8 ; i++)
  1957 		    for (i = 4 ; i < 8 ; i++)
  1958 			    buf[i] = d->transfers[line].data[i - 4];
  1958 			    buf[i] = d->transfers[line].data[i - 4];
  1959 		    d->transfers[line].offset = count;
  1959 		    d->transfers[line].offset = count;
  1960 	    }
  1960 	    }
  1961 	    else { /** Normal transfert */
  1961 	    else { /** Normal transfer */
  1962 		    buf[0] = (1 << 5) | 1;
  1962 		    buf[0] = (1 << 5) | 1;
  1963 		    for (i = 0 ; i < 4 ; i++)
  1963 		    for (i = 0 ; i < 4 ; i++)
  1964 			    buf[i+4] = (UNS8)((count >> (i<<3))); /* i*8 */
  1964 			    buf[i+4] = (UNS8)((count >> (i<<3))); /* i*8 */
  1965 	    }
  1965 	    }
  1966     }
  1966     }
  2270 		MSG_ERR(0x1AF0, "SDO error : No line found for communication with node : ", nodeId);
  2270 		MSG_ERR(0x1AF0, "SDO error : No line found for communication with node : ", nodeId);
  2271         *size = 0;
  2271         *size = 0;
  2272         return SDO_ABORTED_INTERNAL;
  2272         return SDO_ABORTED_INTERNAL;
  2273 	}
  2273 	}
  2274 
  2274 
  2275     /* If transfert not finished just return, but if aborted set abort code and size to 0 */
  2275     /* If transfer not finished just return, but if aborted set abort code and size to 0 */
  2276     if (d->transfers[line].state != SDO_FINISHED) {
  2276     if (d->transfers[line].state != SDO_FINISHED) {
  2277 	    if((d->transfers[line].state == SDO_ABORTED_RCV) || (d->transfers[line].state == SDO_ABORTED_INTERNAL)) {
  2277 	    if((d->transfers[line].state == SDO_ABORTED_RCV) || (d->transfers[line].state == SDO_ABORTED_INTERNAL)) {
  2278             *abortCode = d->transfers[line].abortCode;
  2278             *abortCode = d->transfers[line].abortCode;
  2279             *size = 0;
  2279             *size = 0;
  2280         }
  2280         }