📄 tptx.c
字号:
c2 = clock() + CLOCKS_PER_SEC;
while ( tptx->tx_ecb[0]->inuse != 0 && clock() < c2 )
ipx_dispatch();
tp_set_blk_id(tptx->tx_data[0], TP_ID_ERROR);
tp_set_blk_ver(tptx->tx_data[0], TP_VERSION);
strcpy(tp_get_blk_data_adr(tptx->tx_data[0]), s);
ipx_fill_send_ecb(
tptx->tx_ecb[0],
ipx_get_header(&(tptx->adr), tptx->socket, tptx->socket),
tptx->tx_data[0],
tptx->b_len+TP_BLK_INFO_SIZE);
ipx_send_ecb(tptx->tx_ecb[0]);
if ( cnt >= 0L )
cnt--;
c2 = clock() + CLOCKS_PER_SEC/8;
while ( clock() < c2 )
;
}
}
}
void tptx_TerminateReceiver(tptx_type tptx)
{
tptx_SetState(tptx, tptx_state_none);
{
clock_t c1;
long cnt = 5L;
c1 = clock() + CLOCKS_PER_SEC*2;
while ( clock() < c1 && cnt > 0L )
{
clock_t c2;
ipx_dispatch();
c2 = clock() + CLOCKS_PER_SEC;
while ( tptx->tx_ecb[0]->inuse != 0 && clock() < c2 )
ipx_dispatch();
tp_set_blk_id(tptx->tx_data[0], TP_ID_TERMINATE);
tp_set_blk_ver(tptx->tx_data[0], TP_VERSION);
ipx_fill_send_ecb(
tptx->tx_ecb[0],
ipx_get_header(NULL, tptx->socket, tptx->socket),
tptx->tx_data[0],
tptx->b_len+TP_BLK_INFO_SIZE);
ipx_send_ecb(tptx->tx_ecb[0]);
if ( cnt >= 0L )
cnt--;
c2 = clock() + CLOCKS_PER_SEC/8;
while ( clock() < c2 )
;
}
}
}
int tptx_ListenECB(tptx_type tptx)
{
if ( tptx->rx_ecb->inuse != 0 )
{
return 1;
}
if ( ipx_fill_receive_ecb(
tptx->rx_ecb,
tptx->socket,
tptx->rx_data,
tptx->b_len+TP_BLK_INFO_SIZE) == NULL )
{
tptx_Error(tptx, "cannot fill receive ecb");
return 0;
}
if ( ipx_listen_ecb(tptx->rx_ecb) == 0 )
{
tptx_Error(tptx, "cannot listen to ecb");
return 0;
}
return 1;
}
int tptx_ListenAndSearch(tptx_type tptx, short id1, short id2)
{
if ( tptx->rx_ecb->inuse == 0 )
{
/* printf("inuse: %d \r", tptx->rx_ecb->inuse); */
if ( tptx->rx_ecb->cc == 0 )
{
if (tp_ecb_get_id(tptx->rx_ecb) == TP_ID_ERROR )
{
static char s[80];
sprintf(s, "remote error: '%s'", tp_ecb_get_data_adr(tptx->rx_ecb));
tptx_Error(tptx, s);
return 0;
}
if (tp_ecb_get_id(tptx->rx_ecb) != id1 &&
tp_ecb_get_id(tptx->rx_ecb) != id2 )
{
if ( tptx_ListenECB(tptx) == 0 )
return 0;
}
else
{
return 1;
}
}
else
{
printf(TPTX_ID_STR "receive warning: %s\n",
ipx_get_ecb_cc_string(tptx->rx_ecb));
if ( tptx_ListenECB(tptx) == 0 )
return 0;
}
}
return 0;
}
void tptx_WaitSend(tptx_type tptx,
int no,
void (*next_state)(tptx_type tptx),
void (*repeated_state)(tptx_type tptx),
clock_t delay)
{
if ( tptx->tx_ecb[no]->inuse == 0 )
{
if ( tptx->tx_ecb[no]->cc != 0 )
{
tptx_Error(tptx, ipx_get_ecb_cc_string(tptx->tx_ecb[0]));
}
else
{
tptx->clock_dest = clock()+delay;
tptx_SetRepeatedState(tptx, repeated_state);
tptx_SetState(tptx, next_state);
}
}
}
int tptx_CheckTime(tptx_type tptx)
{
if ( tptx->clock_dest < clock() )
{
tptx_SetState(tptx, tptx_GetRepeatedState(tptx));
return 0;
}
return 1;
}
int tptx_Dispatch(tptx_type tptx)
{
ipx_dispatch();
if ( tptx->is_ended != 0 )
return tptx->is_ended;
tptx->state_fn(tptx);
if ( tptx->state_fn != tptx_state_user_check )
{
if ( kbhit() != 0 )
{
if ( getch() == 27 )
{
tptx_Error(tptx, "user break");
}
}
}
return tptx->is_ended;
}
/* - - - - - state functions - - - - - - - - - - - - - - - - - - - - - - - */
void tptx_state_none(tptx_type tptx)
{
tptx_ListenECB(tptx);
}
void tptx_state_gen_request(tptx_type tptx)
{
tp_request request;
tp_debug_out("tptx_state_gen_request");
request = (tp_request)tp_get_blk_data_adr(tptx->tx_data[0]);
request->adr = *ipx_get_local_net_number();
request->file_size = tptx->f_len;
/* request->flags = 0; */
request->flags = tptx->flags;
if ( tptx->f_name == NULL )
request->flags |= TP_FLAG_IS_DIR;
request->attr = tptx->f_attr;
request->time = tptx->f_time;
request->date = tptx->f_date;
request->short_name_offset = (unsigned)(strlen(tptx->f_logname)+1);
if ( sizeof(tp_request_struct)+(size_t)request->short_name_offset+1 > tptx->b_len )
{
tptx_Error(tptx, "path too long");
return;
}
strcpy(
tp_get_blk_data_adr(tptx->tx_data[0])+sizeof(tp_request_struct),
tptx->f_logname);
strcpy(
tp_get_blk_data_adr(tptx->tx_data[0])+sizeof(tp_request_struct)
+(size_t)request->short_name_offset,
tptx->f_logsname);
/*
printf("lfn:%s normal:%s", tptx->f_logname, tptx->f_logsname);
*/
tp_set_blk_id(tptx->tx_data[0], TP_ID_REQUEST);
tptx_SendECB(tptx, 0);
tptx_SetState(tptx, tptx_state_chk_request);
}
void tptx_state_chk_request(tptx_type tptx)
{
tp_debug_out("tptx_state_chk_request");
tptx_WaitSend(tptx, 0,
tptx_state_wait_ack_request,
tptx_state_gen_request,
tptx->large_delay);
}
void tptx_state_wait_ack_request(tptx_type tptx)
{
/* tp_debug_out("tptx_state_wait_ack_request"); */
if ( tptx_CheckTime(tptx) == 0 )
return;
if ( tptx_ListenAndSearch(tptx, TP_ID_ACK_REQUEST, TP_ID_NONE) != 0 )
{
tp_ack_request ack_request;
ack_request = (tp_ack_request)tp_ecb_get_data_adr(tptx->rx_ecb);
tptx->adr = ack_request->adr;
tptx->is_adr_known = 1;
tptx_ListenECB(tptx);
if ( (ack_request->flags & TP_FLAG_IS_LFN) == 0 )
tptx->flags &= ~TP_FLAG_IS_LFN;
if ( ack_request->exist != 0 &&
(tptx->flags & TP_FLAG_IS_NO_USER_CHECK) == 0 )
{
printf("remote file '%s' exists, overwrite (y,n,a)? ",
tptx->f_logname);
fflush(stdout);
tptx_SetState(tptx, tptx_state_user_check);
}
else
{
tptx_DoPAux(tptx, TP_MSG_PSTART);
tptx_SetState(tptx, tptx_state_gen_file_start);
}
}
}
void tptx_state_user_check(tptx_type tptx)
{
if ( kbhit() != 0 )
{
int c = getch();
switch(c)
{
case 'n':
case 'N':
printf("%c\n", c);
tptx->f_is_skip = 1;
tptx_SetState(tptx, tptx_state_gen_file_end);
return;
case 'a':
case 'A':
printf("%c\n", c);
tptx_SetFlag(tptx, TP_FLAG_IS_NO_USER_CHECK);
tptx_DoPAux(tptx, TP_MSG_PSTART);
tptx_SetState(tptx, tptx_state_gen_file_start);
return;
case 'y':
case 'Y':
case 'j':
case 'J':
printf("%c\n", c);
tptx_DoPAux(tptx, TP_MSG_PSTART);
tptx_SetState(tptx, tptx_state_gen_file_start);
return;
case 27:
tptx_Error(tptx, "user escape");
return;
}
}
if ( tptx_ListenAndSearch(tptx, TP_ID_FILE_START, TP_ID_NONE) != 0 )
{
tp_file_start file_start;
file_start = (tp_file_start)tp_get_blk_data_adr(tptx->rx_data);
tptx->f_is_skip = file_start->is_skip_file;
tptx->flags = file_start->flags;
tptx_ListenECB(tptx);
if ( tptx->f_is_skip != 0 )
{
printf("n\n");
tptx_SetState(tptx, tptx_state_gen_file_end);
}
else
{
printf("y/a\n");
tptx_DoPAux(tptx, TP_MSG_PSTART);
tptx_SetState(tptx, tptx_state_gen_file_start);
}
}
}
void tptx_state_gen_file_start(tptx_type tptx)
{
tp_file_start file_start;
tp_debug_out("tptx_state_gen_file_start");
file_start = (tp_file_start)tp_get_blk_data_adr(tptx->tx_data[0]);
file_start->is_skip_file = 0;
file_start->flags = tptx->flags;
tp_set_blk_id(tptx->tx_data[0], TP_ID_FILE_START);
tptx_SendECB(tptx, 0);
tptx_SetState(tptx, tptx_state_chk_file_start);
}
void tptx_state_chk_file_start(tptx_type tptx)
{
tp_debug_out("tptx_state_chk_file_start");
tptx_WaitSend(tptx, 0,
tptx_state_wait_ack_file_start,
tptx_state_gen_file_start,
tptx->small_delay);
}
void tptx_state_wait_ack_file_start(tptx_type tptx)
{
/* tp_debug_out("tptx_state_wait_ack_file_start"); */
if ( tptx_CheckTime(tptx) == 0 )
return;
if ( tptx_ListenAndSearch(tptx, TP_ID_ACK_FILE_START, TP_ID_NONE) != 0 )
{
tptx->f_start = clock();
tptx_ListenECB(tptx);
tptx_SetState(tptx, tptx_state_gen_block_start);
}
}
void tptx_state_gen_block_start(tptx_type tptx)
{
tp_block_start block_start;
tp_debug_out("tptx_state_gen_block_start");
/* printf("filepos: %ld\n", tptx->f_pos); */
tptx_DoPAux(tptx, TP_MSG_PDATA);
block_start = (tp_block_start)tp_get_blk_data_adr(tptx->tx_data[0]);
block_start->cnt =
(tptx_GetExpectedReadSize(tptx)+tptx->b_len-1)/tptx->b_len;
tp_set_blk_id(tptx->tx_data[0], TP_ID_BLOCK_START);
tptx_SendECB(tptx, 0);
tptx_SetState(tptx, tptx_state_chk_block_start);
}
void tptx_state_chk_block_start(tptx_type tptx)
{
tp_debug_out("tptx_state_chk_block_start");
tptx_WaitSend(tptx, 0,
tptx_state_wait_ack_block_start,
tptx_state_gen_block_start,
tptx->small_delay);
}
void tptx_state_wait_ack_block_start(tptx_type tptx)
{
tp_debug_out("tptx_state_wait_ack_block_start");
if ( tptx_CheckTime(tptx) == 0 )
return;
if ( tptx_ListenAndSearch(tptx, TP_ID_ACK_BLOCK_START, TP_ID_NONE) != 0 )
{
tptx_ListenECB(tptx);
tptx_CopyRead(tptx);
tptx_InitPool(tptx,
(tptx_GetExpectedReadSize(tptx)+tptx->b_len-1)/tptx->b_len,
NULL);
tptx_SetState(tptx, tptx_state_gen_data);
}
}
void tptx_state_gen_data(tptx_type tptx)
{
/* tp_debug_out("tptx_state_gen_data"); */
if ( tptx->b_list_cnt < tptx->b_curr_cnt )
{
tp_data data;
/*
printf("(%d,%d/%d)", (int)tptx->b_list_ptr[tptx->b_list_cnt],
tptx->b_list_cnt, tptx->b_curr_cnt);
*/
data = (tp_data)tp_get_blk_data_adr(tptx->tx_data[tptx->b_list_cnt]);
data->no = tptx->b_list_ptr[tptx->b_list_cnt];
if ( tptx->b_pool_size-(size_t)(((size_t)data->no)*tptx->b_len) <
tptx->b_len )
data->len = tptx->b_pool_size-(size_t)(((size_t)data->no)*tptx->b_len);
else
data->len = tptx->b_len;
tptx_CopyMemoryFromPool(tptx,
data->no,
tp_get_blk_data_adr(tptx->tx_data[tptx->b_list_cnt])+sizeof(tp_data_struct),
data->len);
tp_set_blk_id(tptx->tx_data[tptx->b_list_cnt], TP_ID_DATA);
tptx_SendECB(tptx, tptx->b_list_cnt);
tptx->b_list_cnt++;
}
else
{
tptx_SetState(tptx, tptx_state_chk_data);
tptx_Read(tptx);
}
}
void tptx_state_chk_data(tptx_type tptx)
{
int i, c;
/* tp_debug_out("tptx_state_chk_data"); */
c = 0;
for( i = 0; i < tptx->b_curr_cnt; i++ )
{
if ( tptx->tx_ecb[i]->inuse == 0 )
{
if ( tptx->tx_ecb[i]->cc != 0 )
{
tptx_Error(tptx, ipx_get_ecb_cc_string(tptx->tx_ecb[0]));
}
else
{
c++;
}
}
}
if ( c == tptx->b_curr_cnt )
{
tptx_SetState(tptx, tptx_state_gen_block_end);
}
}
void tptx_state_gen_block_end(tptx_type tptx)
{
tp_block_end block_end;
tp_debug_out("tptx_state_gen_block_end");
block_end = (tp_block_end)tp_get_blk_data_adr(tptx->tx_data[0]);
block_end->crc = tptx->f_crc;
tp_set_blk_id(tptx->tx_data[0], TP_ID_BLOCK_END);
tptx_SendECB(tptx, 0);
tptx_SetState(tptx, tptx_state_chk_block_end);
}
void tptx_state_chk_block_end(tptx_type tptx)
{
tp_debug_out("tptx_state_chk_block_end");
tptx_WaitSend(tptx, 0,
tptx_state_wait_ack_block_end,
tptx_state_gen_block_end,
tptx->small_delay);
}
void tptx_state_wait_ack_block_end(tptx_type tptx)
{
/* tp_debug_out("tptx_state_wait_ack_block_end"); */
if ( tptx_CheckTime(tptx) == 0 )
return;
if ( tptx_ListenAndSearch(tptx, TP_ID_ACK_BLOCK_END, TP_ID_MISSED_BLOCKS) != 0 )
{
if ( tp_ecb_get_id(tptx->rx_ecb) == TP_ID_MISSED_BLOCKS )
{
tp_missed_blocks missed_blocks;
missed_blocks = (tp_missed_blocks)tp_ecb_get_data_adr(tptx->rx_ecb);
/* printf("missed: %d\n", (int)missed_blocks->cnt); */
tptx_InitPool(tptx,
missed_blocks->cnt,
(short *)(tp_ecb_get_data_adr(tptx->rx_ecb)+
sizeof(tp_missed_blocks_struct)));
tptx_SetState(tptx, tptx_state_gen_data);
tptx_ListenECB(tptx);
return;
}
else if ( tp_ecb_get_id(tptx->rx_ecb) == TP_ID_ACK_BLOCK_END )
{
if ( tptx->f_pos >= tptx->f_len )
{
tptx_SetState(tptx, tptx_state_gen_file_end);
}
else
{
tptx_SetState(tptx, tptx_state_gen_block_start);
}
tptx_ListenECB(tptx);
}
}
}
void tptx_state_gen_file_end(tptx_type tptx)
{
tp_debug_out("tptx_state_gen_file_end");
tp_set_blk_id(tptx->tx_data[0], TP_ID_FILE_END);
tptx_SendECB(tptx, 0);
tptx_SetState(tptx, tptx_state_chk_file_end);
}
void tptx_state_chk_file_end(tptx_type tptx)
{
tp_debug_out("tptx_state_chk_file_end");
tptx_WaitSend(tptx, 0,
tptx_state_wait_ack_file_end,
tptx_state_gen_file_end,
tptx->large_delay);
}
void tptx_state_wait_ack_file_end(tptx_type tptx)
{
tp_debug_out("tptx_state_wait_ack_file_end");
if ( tptx_CheckTime(tptx) == 0 )
return;
if ( tptx_ListenAndSearch(tptx, TP_ID_ACK_FILE_END, TP_ID_NONE) != 0 )
{
if ( tptx->f_is_skip == 0 )
{
tptx_DoPAux(tptx, TP_MSG_PDATA);
tptx_DoPAux(tptx, TP_MSG_PEND);
}
tptx_CloseFile(tptx);
tptx_ListenECB(tptx);
tptx_SetState(tptx, tptx_state_none);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -