📄 ftpsocket.c
字号:
if (nResult <0 )
{
Print(L"Socket Error, can't get recever state\n\r");
Status = FALSE;
goto Exit;
}
if (subcmdcode != SUCCESS)
{
Print(L"Recever not ready!Download fail!\n\r");
Status = FALSE;
goto Exit;
}
//开始传文件
while(1)
{
Size = PAGESIZE*1024;
pBuffer = MEM_ALLOC(Size);
totallen = kwfread( pBuffer, sizeof( CHAR8 ), Size, FileHandle );
//读到了末尾
if(totallen<=0)
{
MEM_FREE(pBuffer);
Print(L"Send file %s finish!\n\r",FileName);
//send a error to recever
hd.subcmdcode = DOWNLOADFILE_FINISH;
nResult = SocketSend(SocketId, (CHAR8*)&hd, sizeof(SocketPackageHead));
Status = 0;
if (nResult <0 )
{
Print(L"Socket Error, can't send finish message!\n\r");
Status = FALSE;
}
goto Exit;
}
hd.subcmdcode = SUCCESS;
hd.packageLength = sizeof(hd) + totallen;
nResult = SocketSend(SocketId, (CHAR8*)&hd, sizeof(hd));
if (nResult <0 )
{
Print(L"Socket Error, can't send packagehead!\n\r");
Status = FALSE;
}
nResult = SocketSend(SocketId, pBuffer, totallen);
if (nResult <0 )
{
Print(L"Socket Error, can't send pBuffer!\n\r");
Status = FALSE;
}
MEM_FREE(pBuffer);
//接收接收方的反馈
nResult = SocketRecvAll(SocketId, (CHAR8*)&hd, sizeof(SocketPackageHead));
if (nResult <0)
{
Print(L"recv package feedback socket error!\n");
Status = FALSE;
goto Exit;
}
if (hd.subcmdcode !=SUCCESS)
{
Print(L"recv package receve error!\n");
Status = FALSE;
goto Exit;
}
//检查是否到了文件尾
if(kwfeof(FileHandle))
{
Print(L"Send file %s finish!\n\r",FileName);
//send a error to recever
hd.subcmdcode = DOWNLOADFILE_FINISH;
nResult = SocketSend(SocketId, (CHAR8*)&hd, sizeof(SocketPackageHead));
Status = TRUE;
if (nResult <0 )
{
Print(L"Socket Error, can't send finish message!\n\r");
Status = FALSE;
}
goto Exit;
}
Sended+=totallen;
Print(L"\r Progress: %d%%",(Sended*100)/FileLength);
}
//
//
Exit:
kwfclose(FileHandle);
return Status;
}
/*
//浏览当前目录
INT32 ListCurrentDirectory(SOCKET_ID SocketId,FileMgrControl *m_FileMgr)
{
INT32 ItemCount;
INT32 nResult;
INT32 Status;
//SocketPackageHead hd;
//CHAR16 *MessageStr;
CHAR16 MessageStr[512];
LIST_ENTRY *ItemLink;
ContentListITEM *ProtItem;
//获取当前目录中的所有条款个数
ItemCount = m_FileMgr->m_ContentList.GetCount(&(m_FileMgr->m_ContentList));
//向接收方说明条款的个数
nResult = SocketSend(SocketId, (CHAR8*)&ItemCount, sizeof(INT32));
if (nResult <0 )
{
Print(L"Socket Error, can't send countnum %d\n\r",ItemCount);
Status = FALSE;
return Status;
}
//MessageStr = MEM_ALLOC(512);
//逐一发送给接受方
//for(i=0;i<ItemCount;i++)
for (ItemLink = m_FileMgr->m_ContentList.LinkItems.Flink;
ItemLink != &m_FileMgr->m_ContentList.LinkItems;
ItemLink = ItemLink->Flink)
{
//接受方OK了
nResult = SocketRecv(SocketId, (CHAR8*)&Status, sizeof(INT32));
if (nResult <0 )
{
Print(L"Socket Error, accepter not ready.\n");
Status = FALSE;
//MEM_FREE(MessageStr);
return Status;
}
if(Status!=SUCCESS)
{
Print(L"Recevier not ready.\n");
Status = FALSE;
//MEM_FREE(MessageStr);
return Status;
}
ProtItem = CR(ItemLink, ContentListITEM, Link, EFI_CONTENTLISTITEM_SIGNATURE);
StrCpy(MessageStr,ProtItem->ItemText);
if(!SendMessage(SocketId,MessageStr,GetFileSize(MessageStr),ProtItem->ItemData))
{
Print(L"Send list fail.\n");
Status = FALSE;
//MEM_FREE(MessageStr);
return Status;
}
//Print(L"%s\n",MessageStr);
}
//MEM_FREE(MessageStr);
Print(L"Total %d Files\n",ItemCount);
return TRUE;
}
*/
//浏览当前目录
INT32 ListCurrentDirectory(SOCKET_ID SocketId,FileMgrControl *m_FileMgr)
{
INT32 ItemCount;
INT32 nResult;
INT32 Status;
CHAR8 *ListContentBuffer;//列表内容,一次性开辟,一次性传输
LIST_ENTRY *ItemLink;
ContentListITEM *ProtItem;
FileListUnit m_ListUnit;//列表单元
INT32 Offset=0;
INT32 TotalSize=0,SendSize=0;
INT32 CmdCode,SubCmdCode;
//获取当前目录中的所有条款个数
ItemCount = m_FileMgr->m_ContentList.GetCount(&(m_FileMgr->m_ContentList));
//开辟列表一次性空间
ListContentBuffer = MEM_ALLOC(sizeof(FileListUnit)*ItemCount);
//向接收方说明条款的个数
nResult = SocketSend(SocketId, (CHAR8*)&ItemCount, sizeof(INT32));
if (nResult <0 )
{
Print(L"Socket Error, can't send countnum %d\n\r",ItemCount);
Status = FALSE;
return Status;
}
Print(L"Total %d Files\n",ItemCount);
//逐个存入这个缓存
for (ItemLink = m_FileMgr->m_ContentList.LinkItems.Flink;
ItemLink != &m_FileMgr->m_ContentList.LinkItems;
ItemLink = ItemLink->Flink)
{
ProtItem = CR(ItemLink, ContentListITEM, Link, EFI_CONTENTLISTITEM_SIGNATURE);
//先保存名称,再保存数据
String16To8(ProtItem->ItemText,m_ListUnit.FileName);
m_ListUnit.FileSize = (INT32)GetFileSize(ProtItem->ItemText);
m_ListUnit.FileType = ProtItem->ItemData;
memcpy(ListContentBuffer+Offset,&m_ListUnit,sizeof(FileListUnit));
Offset+=sizeof(FileListUnit);
}
Offset = 0;
if(ItemCount<FILEUNITMAXCOUNT)
{
SendSize = ItemCount*sizeof(FileListUnit);
}
else SendSize = FILEUNITMAXCOUNT*sizeof(FileListUnit);
while(1)
{
nResult = SocketSend(SocketId, ListContentBuffer+Offset, SendSize);
Print(L"Send Offset:%d\n",Offset);
if(nResult == SOCKET_ERROR)
{
Status = FALSE;
goto Exit;
}
nResult = SocketRecv(SocketId, (CHAR8*)&CmdCode, sizeof(INT32));
//Print(L"Recv nResult:%d\n",nResult);
if(nResult == SOCKET_ERROR)
{
Status = FALSE;
goto Exit;
}
Print(L"Recv CmdCode:%d\n",CmdCode);
if(CmdCode == SUCCESS)
{
Status = TRUE;
goto Exit;
}
Offset+=SendSize;
ItemCount-=SendSize/(sizeof(FileListUnit));
if(ItemCount==0)
{
Status = TRUE;
goto Exit;
}
else if(ItemCount<FILEUNITMAXCOUNT)
{
SendSize = ItemCount*sizeof(FileListUnit);
}
else SendSize = FILEUNITMAXCOUNT*sizeof(FileListUnit);
}
//收到确认信息
Exit: MEM_FREE(ListContentBuffer);
return Status;
}
//打开一个文件夹,在当前文件夹下
void OpenSubDirectory(FileMgrControl *m_FileMgr,
CHAR16 *SubDirectoryName)//文件夹名称
{
OpenSubDir(m_FileMgr,SubDirectoryName);
}
//检查用户名和密码是否正确,正确返回TRUE
BOOLEAN IsPassWordRight(CHAR16 *strAccess)
{
CHAR16 strUserName[256];
CHAR16 strPassWord[256];
INTN i,len,j;
if(!strPassWord)return FALSE;
StrCpy(strUserName,L"");
StrCpy(strPassWord,L"");
len = StrLen(strAccess);
Print(L"strAccess= %s\n",strAccess);
//以":"为分隔符得到用户名和密码
for(i=0;i<len;i++)
{
if(strAccess[i]==':')
{
strUserName[i]='\0';
i++;
break;
}
strUserName[i]=strAccess[i];
}
strUserName[i]='\0';
for(j=0;(j<len)&&(i<len);i++,j++)
{
strPassWord[j]=strAccess[i];
}
strPassWord[j]='\0';
Print(L"%s:%s\n",strUserName,strPassWord);
if((strcmp(strUserName,L"admin")==0)
&&(strcmp(strPassWord,L"efiserver")==0))return TRUE;
else return FALSE;
}
//使用select模型,判断socket是否可用,根据超时sec,如果sec为-1则代表阻塞等待下去
BOOLEAN IsSocketEnable(SOCKET_ID socketID, INT32 sec, INT32 usec,INT32 selectmodel)
{
INT32 st = 0;
struct timeval to;
fd_set fs;
to.tv_sec = sec;
to.tv_usec = usec;
FD_ZERO(&fs);
FD_SET(socketID, &fs);
switch(selectmodel)
{
case READ_STATUS:
if (sec<0)
{
st = select(socketID+1, &fs, 0, 0, NULL);
}
else
st = select(socketID+1, &fs, 0, 0, &to);
break;
case WRITE_STATUS:
if (sec<0)
{
st = select(socketID+1, 0, &fs, 0, NULL);
}
else
st = select(socketID+1, 0, &fs, 0, &to);
break;
case EXCPT_STATUS:
if (sec<0)
{
st = select(socketID+1, 0, 0, &fs, NULL);
}
else
st = select(socketID+1, 0, 0, &fs, &to);
break;
}
if (st)
{
if (FD_ISSET(socketID, &fs))
{
return TRUE;
}
}
return FALSE;
}
//包装过的socket接收与发送,使用select模型,根据等待时间,不会死锁
INT32 SocketRecv(SOCKET_ID socketID,CHAR8 *pBuffer,INT32 nLength)
{
if (IsSocketEnable(socketID, nWaitSecond, 0, READ_STATUS))
{
return Socket_read(socketID,pBuffer, nLength);
}
else if(!IsSocketEnable(socketID, nWaitSecond, 0, EXCPT_STATUS))
{
return 0;
}
return SOCKET_ERROR;
}
INT32 SocketSend(SOCKET_ID socketID,CHAR8 *pBuffer,INT32 nLength)
{
if (IsSocketEnable(socketID, nWaitSecond, 0, WRITE_STATUS))
{
return Socket_write(socketID,pBuffer, nLength);
}else if(!IsSocketEnable(socketID, nWaitSecond, 0, EXCPT_STATUS))
{
return 0;
}
return SOCKET_ERROR;
}
//接收一个连接,阻塞等待
INT32 AcceptConnect(SOCKET_ID ListenserSocketID,struct sockaddr* paddr,INT32 *nLength)
{
if (IsSocketEnable(ListenserSocketID, nWaitSecond, 0, READ_STATUS))
{
return accept (ListenserSocketID, paddr, nLength);
}
return SOCKET_ERROR;
}
//发送磁盘分区表
BOOLEAN SendDiskPartitionTable(SOCKET_ID SocketId,DiskPartitionTable *DPT)
{
//CHAR8 *pDPTBuffer=NULL;
INT32 nResult,CmdCode;
BOOLEAN Status;
//pDPTBuffer=MEM_ALLOC(sizeof(DiskPartitionTable));
//if(pDPTBuffer==NULL)return FALSE;
//发送DPT
nResult = SocketSend(SocketId, (CHAR8*)DPT, sizeof(DiskPartitionTable));
// Print(L"Send Offset:%d\n",Offset);
if(nResult == SOCKET_ERROR)
{
Status = FALSE;
goto Exit;
}
//接受回应
nResult = SocketRecv(SocketId, (CHAR8*)&CmdCode, sizeof(INT32));
if(nResult == SOCKET_ERROR)
{
Status = FALSE;
goto Exit;
}
if(CmdCode == SUCCESS)
{
Status = TRUE;
goto Exit;
}
Exit: //MEM_FREE(pDPTBuffer);
return Status;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -