FTPClient.c

FTPClient.c example details
FTP Client description

/***************************************************************************//**
@file FTPClient.c
@brief FTP client example
@verbatim
_ _ _
__| | ___(_) ____ _ __ | |_
/ _` | / __| |/ _` | '_ \| __|
| (_| | _ \__ \ | (_| | | | | |_
\__,_|(_) ___/_|\__, |_| |_|\__|
Signalprocessing |___/ Technology
@endverbatim
@author D.SignT GmbH & Co. KG, Claus Hermbusche
@date 2019-06-03
@anchor FTPCLIEX
@cond Software License Agreement
Copyright (C) 2001-2019 D.SignT GmbH & Co. KG - http://www.dsignt.de
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:
Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the
distribution.
Neither the name of D.SignT GmbH & Co. KG nor the names of its
contributors may be used to endorse or promote products derived
from this software without specific prior written permission.
Disclaimer
THIS SOFTWARE IS PROVIDED BY D.SIGNT GMBH & CO. KG "AS IS" AND ANY
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL D.SIGNT GMBH & CO. KG BE
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE
OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
@endcond
*******************************************************************************/
/*******************************************************************************
include stdtypes.h to avoid data type mismatch
*******************************************************************************/
/*******************************************************************************
include Runtime Source
*******************************************************************************/
#include <stdlib.h>
#include <stdio.h>
#include <stddef.h>
#include <inttypes.h>
#include <time.h>
/*******************************************************************************
network support functions
*******************************************************************************/
#include <Libs/NETlib/net.h> /* D.Module network support */
#include <Libs/NETlib/ftplib.h> /* FTP support */
/*******************************************************************************
board specific functions
*******************************************************************************/
#include <BoardSupport/inc/BoardSpecific.h> /* board support functions */
/*******************************************************************************
common support functions
*******************************************************************************/
#include <Common/Common.h> /* on exit function */
#include <Common/uartio.h> /* UART support */
#include <Common/timer.h> /* timer setting */
#include <Common/CPrintf.h> /* CPrintf defines */
/*******************************************************************************
network configuration
*******************************************************************************/
#include <BoardSupport/config/netconfig.c> /* network configuration */
#ifdef __cplusplus
extern "C" {
#endif /* !__cplusplus */
/*******************************************************************************
local prototypes
*******************************************************************************/
#pragma CODE_SECTION(FTP_receive_file, ".nettextslow");
#pragma CODE_SECTION(FTP_send_file, ".nettextslow");
#ifdef __cplusplus
} // extern "C"
#endif
/*******************************************************************************
* *
* DEFINES *
* *
*******************************************************************************/
/*******************************************************************************
create 32bit wide identifiers for up- and downloads. some processors require
these identifiers to be 32 bit wide.
*******************************************************************************/
#define FTP_DOWNLOAD UINT32_C(1)
#define FTP_UPLOAD UINT32_C(2)
/*******************************************************************************
* *
* GLOBALS *
* *
*******************************************************************************/
/*******************************************************************************
program name
*******************************************************************************/
char *program_name = "FTP-client";
/*******************************************************************************
target buffer location is .data_slow (ref. ftpclient.cmd)
*******************************************************************************/
#ifdef __cplusplus
#pragma DATA_SECTION(".data_slow");
#else
#pragma DATA_SECTION(data_buffer, ".data_slow");
#endif
/*******************************************************************************
target buffer
*******************************************************************************/
/*******************************************************************************
use action to perform download (action = 1) or upload (action = 2)
*******************************************************************************/
/*******************************************************************************
FTP server IP address; change to your FTP server address
*******************************************************************************/
static char ftp_server_ip_addr[] = "192.168.168.8";
/*******************************************************************************
define a login user
user_type user[] =
{
// {"loginname, password, zero termination},
{"admin", "xxxx" , EFS_TERMINATION},
EFS_TERMINATION // terminating zero!
};
*******************************************************************************/
{
{"anonymous", "*" , EFS_TERMINATION},
EFS_TERMINATION /* terminating zero! */
};
/*******************************************************************************
* *
* FUNCTIONS *
* *
*******************************************************************************/
/*******************************************************************************
@brief receive a File from FTP server
@param -
@return FALSE: out of memory
@return return code from FTP server
*******************************************************************************/
{
/***************************************************************************
locals
***************************************************************************/
int32_t ret = FALSE; /* return code from server */
FTP_client_type *FTP_client; /* FTP client connection */
/***************************************************************************
get FTP client. Parameter is FTP server IP address and login user
***************************************************************************/
FTP_client = FTP_get_control (ftp_server_ip_addr, user);
if ( FTP_client == NULL )
{
/***********************************************************************
out of memory
***********************************************************************/
"Out of memory error\r\n"
return (FALSE);
}
/***************************************************************************
try to connect
***************************************************************************/
CPuts ( "Connecting..." );
switch ( FTP_connect ( FTP_client, CONNECT_TIMEOUT) )
{
case TRUE: // success
/*******************************************************************
connection successful-> try to login
*******************************************************************/
if ( FTP_server_login (FTP_client) == FTP_LOGIN_OK )
{
/***************************************************************
Login successful
***************************************************************/
/***************************************************************
set file buffer for received data
***************************************************************/
FTP_set_file_buffer ( FTP_client,
/***************************************************************
retrieve file
check syntax of file name, some servers need a slash
"/ftproot/readme.txt"
***************************************************************/
ret = FTP_retrieve_file (FTP_client, "\\ftproot\\readme.txt", 'A');
/***************************************************************
check return code
***************************************************************/
switch ( ret )
{
CPrintf ( "Retrieving readme.txt ( %"PRId32" bytes) successful\r\n", FTP_client-> file_size );
break;
CPuts ( "Error: Port in use\r\n");
break;
CPuts ( "Error: Invalid path\r\n");
break;
default :
CPuts ( "Retrieving readme.txt failure\r\n" );
break;
} // switch
/***************************************************************
don't forget to logout
***************************************************************/
FTP_server_logout (FTP_client);
}
else
{
CPuts( "FTP server login failed\r\n" );
}
break;
default : // error
CPuts ("Error connecting FTP server:\r\n");
net_print_error (FTP_client-> control -> error_code, CPrintf);
break;
} // switch
/***************************************************************************
free FTP client
***************************************************************************/
FTP_free_control (FTP_client);
return (ret);
}
/*******************************************************************************
@brief send data to FTP server
@param -
@return FALSE: out of memory
@return return code from FTP server
*******************************************************************************/
{
/***************************************************************************
locals
***************************************************************************/
int32_t ret = FALSE; /* return code from server */
FTP_client_type *FTP_client; /* FTP client connection */
/***************************************************************************
get FTP client. Parameter is FTP server IP address and login user
***************************************************************************/
FTP_client = FTP_get_control(ftp_server_ip_addr, user);
if ( FTP_client == NULL )
{
/***********************************************************************
out of memory
***********************************************************************/
"Out of memory error\r\n"
return (FALSE);
}
/***************************************************************************
try to connect
***************************************************************************/
CPuts( "Connecting..." );
switch ( FTP_connect ( FTP_client, CONNECT_TIMEOUT) )
{
case TRUE: // success
/*******************************************************************
connection successful-> try to login
*******************************************************************/
if ( FTP_server_login (FTP_client) == FTP_LOGIN_OK)
{
/***************************************************************
Login successful
***************************************************************/
/***************************************************************
set file buffer for received data
***************************************************************/
FTP_set_file_buffer ( FTP_client,
/***************************************************************
send file
check syntax of file name, some servers need a slash
"/ftproot/logfile"
***************************************************************/
ret = FTP_store_file (FTP_client, "\\ftproot\\logfile.bin", 'I');
/***************************************************************
check return code
***************************************************************/
switch ( ret )
{
CPrintf( "sending logfile.bin ( %"PRId32" bytes) successful\r\n", FTP_client-> file_size );
break;
CPuts ( "Error: Port in use\r\n");
break;
CPuts ( "Error: Invalid path\r\n");
break;
default :
CPuts ( "sending logfile.bin failure\r\n" );
break;
} // switch
/***************************************************************
don't forget to logout
***************************************************************/
FTP_server_logout (FTP_client);
}
else
{
CPuts ( "FTP server login failed\r\n" );
}
break;
default : // error
CPuts ( "Error connecting FTP server:\r\n");
net_print_error (FTP_client-> control -> error_code, CPrintf);
break;
} // switch
/***************************************************************************
free FTP client
***************************************************************************/
FTP_free_control (FTP_client);
return (ret);
}
/*******************************************************************************
@brief Main application
@param -
@return never
*******************************************************************************/
#pragma CODE_SECTION(main , ".commontext");
int main ( void )
{
/***************************************************************************
locals
***************************************************************************/
int main_loop = 1; /* main loop switch, set to 0 to exit */
volatile uint32_t ret; /* FTP server result */
timeval stamp1, stamp2, delta; /* used to determine startup time */
#ifdef USE_UART_CONTROL
char c;
#endif
/***************************************************************************
initialize application (e.g. timer clocks, PLL settings, EMIF etc.)
(ref. \Common\Common.c)
***************************************************************************/
/***************************************************************************
select output device for CPrintf (ref. \Common\cprintf.c)
possible settings:
CPRINTF_UART_OUTPUT -> output to UART
CPRINTF_CCS_OUTPUT -> output to CCS
CPRINTF_UART_OUTPUT | CPRINTF_CCS_OUTPUT -> output to UART and CCS
***************************************************************************/
/***************************************************************************
print a start up message
***************************************************************************/
/**************************************************************************/
// CPrintfProgress (" Heap check ");
// at least 0x8000 bytes required for this app
/**************************************************************************/
// CPrintfProgressSuccess();
/**************************************************************************/
CPrintfProgress (" Setup system time ");
// 1 milli seconds resolution
/**************************************************************************/
CPrintf (" *** timer %d mapped to CPU int %d ***\r\n",
/**************************************************************************/
CPrintfProgress (" Enable interrupts ");
/**************************************************************************/
/**************************************************************************/
CPrintfProgress (" Start system timer ");
/**************************************************************************/
CPrintf (" *** timer %d running at %"PRId32" Hz ***\r\n", SystemTimerDev, RES_SECONDS/GetSystemTimerRes());
/***************************************************************************
measure network initialization time
***************************************************************************/
stamp1 = GetTimeStamp();
/**************************************************************************/
CPrintfProgress (" Initialize network ");
/**************************************************************************/
InitializeNetwork (64); // 64 bytes for ping
stamp2 = GetTimeStamp();
tv_interval (&delta, &stamp1, &stamp2);
CPuts (" network startup time [sec]: ");
"%"PRId32".%03"PRId32"\r\n"
delta.tv_sec,
delta.tv_usec/UINT32_C(1000));
#ifdef USE_UART_CONTROL
CPrintf (" press <"VT100_BLUE"1"VT100_DEFAULT"> to retrieve a file from FTP server (%s)\r\n", ftp_server_ip_addr);
CPrintf (" press <"VT100_BLUE"2"VT100_DEFAULT"> to send a file to FTP server (%s)\r\n", ftp_server_ip_addr);
#else
CPuts ("\r\n use test.gel to set action\r\n");
CPrintf (" enter <1> to retrieve a file from FTP server (%s)\r\n", ftp_server_ip_addr);
CPrintf (" enter <2> to send a file to FTP server (%s)\r\n", ftp_server_ip_addr);
#endif
/***************************************************************************
main program loop: set main_loop to 0 to exit loop
***************************************************************************/
CPrintf ("\r\n %s running...", program_name);
CPuts (" entering main loop ...\r\n");
while ( main_loop )
{
/***********************************************************************
try to detect IP assignment
if DHCP is used, the assigned IP address may change
***********************************************************************/
/***********************************************************************
process net_isq()
***********************************************************************/
net_isq ();
/***********************************************************************
monitor link status
***********************************************************************/
/***********************************************************************
handle FTP up/download (use test.gel to set action)
***********************************************************************/
switch ( action )
{
action = FALSE;
break;
case FTP_UPLOAD:
action = FALSE;
ret = FTP_send_file();
break;
default :
action = FALSE;
break;
} // switch
#ifdef USE_KEY_CONTROL
if ( KEY_pressed (SW1) ) action = FTP_UPLOAD;
#endif
#ifdef USE_UART_CONTROL
{
CPrintf("%c\r\n",c);
action = (uint32_t)(c - '0');
}
#endif
/***********************************************************************
show that the program is running, perform symbol animation
***********************************************************************/
}
/***************************************************************************
exit program, shut down peripherals
***************************************************************************/
return (0);
}