- updated client example for IEC 61850 file services
This commit is contained in:
parent
2a40798f10
commit
6badf692fe
5 changed files with 267 additions and 113 deletions
|
@ -1,6 +1,6 @@
|
|||
|
||||
set(iec61850_client_example_files_SRCS
|
||||
client_example_files.c
|
||||
file-tool.c
|
||||
)
|
||||
|
||||
IF(MSVC)
|
||||
|
@ -8,10 +8,10 @@ set_source_files_properties(${iec61850_client_example_files_SRCS}
|
|||
PROPERTIES LANGUAGE CXX)
|
||||
ENDIF(MSVC)
|
||||
|
||||
add_executable(iec61850_client_example_files
|
||||
add_executable(file-tool
|
||||
${iec61850_client_example_files_SRCS}
|
||||
)
|
||||
|
||||
target_link_libraries(iec61850_client_example_files
|
||||
target_link_libraries(file-tool
|
||||
iec61850
|
||||
)
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
LIBIEC_HOME=../..
|
||||
|
||||
PROJECT_BINARY_NAME = client_example_files
|
||||
PROJECT_SOURCES = client_example_files.c
|
||||
PROJECT_BINARY_NAME = file-tool
|
||||
PROJECT_SOURCES = file-tool.c
|
||||
|
||||
include $(LIBIEC_HOME)/make/target_system.mk
|
||||
include $(LIBIEC_HOME)/make/stack_includes.mk
|
||||
|
|
|
@ -1,107 +0,0 @@
|
|||
/*
|
||||
* client_example_files.c
|
||||
*
|
||||
* This example demonstrates the usage of the file services
|
||||
*
|
||||
* - How to browse the file system of the server
|
||||
* - How to download a file from the server
|
||||
*
|
||||
* Note: intended to be used with server_example3
|
||||
*
|
||||
*/
|
||||
|
||||
#include "iec61850_client.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include "hal_thread.h"
|
||||
|
||||
#define MAX_BUFFER_SIZE 2000000
|
||||
|
||||
static uint8_t downloadBuffer[MAX_BUFFER_SIZE];
|
||||
static int bufferPosition = 0;
|
||||
|
||||
static bool
|
||||
downloadHandler(void* parameter, uint8_t* buffer, uint32_t bytesRead)
|
||||
{
|
||||
printf("received %i bytes\n", bytesRead);
|
||||
|
||||
if (bufferPosition + bytesRead < MAX_BUFFER_SIZE) {
|
||||
memcpy(downloadBuffer + bufferPosition, buffer, bytesRead);
|
||||
|
||||
bufferPosition += bytesRead;
|
||||
|
||||
return true;
|
||||
}
|
||||
else
|
||||
return false;
|
||||
}
|
||||
|
||||
int main(int argc, char** argv) {
|
||||
|
||||
char* hostname;
|
||||
int tcpPort = 102;
|
||||
|
||||
if (argc > 1)
|
||||
hostname = argv[1];
|
||||
else
|
||||
hostname = "localhost";
|
||||
|
||||
if (argc > 2)
|
||||
tcpPort = atoi(argv[2]);
|
||||
|
||||
IedClientError error;
|
||||
|
||||
IedConnection con = IedConnection_create();
|
||||
|
||||
IedConnection_connect(con, &error, hostname, tcpPort);
|
||||
|
||||
if (error == IED_ERROR_OK) {
|
||||
|
||||
/* Get the root directory */
|
||||
LinkedList rootDirectory =
|
||||
IedConnection_getFileDirectory(con, &error, NULL);
|
||||
|
||||
if (error != IED_ERROR_OK) {
|
||||
printf("Error retrieving file directory\n");
|
||||
goto abort_connection;
|
||||
}
|
||||
|
||||
|
||||
LinkedList directoryEntry = LinkedList_getNext(rootDirectory);
|
||||
|
||||
while (directoryEntry != NULL) {
|
||||
|
||||
FileDirectoryEntry entry = (FileDirectoryEntry) directoryEntry->data;
|
||||
|
||||
printf("%s %i\n", FileDirectoryEntry_getFileName(entry), FileDirectoryEntry_getFileSize(entry));
|
||||
|
||||
directoryEntry = LinkedList_getNext(directoryEntry);
|
||||
}
|
||||
|
||||
|
||||
/* Download a file from the server */
|
||||
IedConnection_getFile(con, &error, "IEDSERVER.BIN", downloadHandler, NULL);
|
||||
|
||||
if (error != IED_ERROR_OK)
|
||||
printf("Failed to get file!\n");
|
||||
|
||||
/* Delete file at server */
|
||||
IedConnection_deleteFile(con, &error, "IEDSERVER.BIN");
|
||||
|
||||
if (error != IED_ERROR_OK)
|
||||
printf("Failed to delete file! (code=%i)\n", error);
|
||||
|
||||
abort_connection:
|
||||
|
||||
IedConnection_abort(con, &error);
|
||||
}
|
||||
else {
|
||||
printf("Failed to connect to %s:%i\n", hostname, tcpPort);
|
||||
}
|
||||
|
||||
IedConnection_destroy(con);
|
||||
}
|
||||
|
||||
|
261
examples/iec61850_client_example_files/file-tool.c
Normal file
261
examples/iec61850_client_example_files/file-tool.c
Normal file
|
@ -0,0 +1,261 @@
|
|||
/*
|
||||
* file-tool.c
|
||||
*
|
||||
* This example demonstrates the usage of the file services
|
||||
*
|
||||
* - How to browse the file system of the server
|
||||
* - How to download a file from the server
|
||||
*
|
||||
* Note: intended to be used with server_example3 or server_example_files
|
||||
*
|
||||
*/
|
||||
|
||||
#include "iec61850_client.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <libgen.h>
|
||||
|
||||
static char* hostname = "localhost";
|
||||
static int tcpPort = 102;
|
||||
static char* filename = NULL;
|
||||
|
||||
typedef enum {
|
||||
FileOperationType_None = 0,
|
||||
FileOperationType_Dir,
|
||||
FileOperationType_Info,
|
||||
FileOperationType_Del,
|
||||
FileOperationType_Get,
|
||||
FileOperationType_Set
|
||||
} FileOperationType;
|
||||
|
||||
static FileOperationType operation = FileOperationType_None;
|
||||
|
||||
|
||||
|
||||
static bool
|
||||
downloadHandler(void* parameter, uint8_t* buffer, uint32_t bytesRead)
|
||||
{
|
||||
FILE* fp = (FILE*) parameter;
|
||||
|
||||
printf("received %i bytes\n", bytesRead);
|
||||
|
||||
if (fwrite(buffer, bytesRead, 1, fp) == 1)
|
||||
return true;
|
||||
else {
|
||||
printf("Failed to write local file!\n");
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
static void
|
||||
printHelp()
|
||||
{
|
||||
printf("file-tool [options] <operation> [<parameters>]\n");
|
||||
printf(" Options:\n");
|
||||
printf(" -h <hostname/IP>\n");
|
||||
printf(" -p portnumber\n");
|
||||
printf(" Operations\n");
|
||||
printf(" dir - show directory\n");
|
||||
printf(" info <filename> - show file info\n");
|
||||
printf(" del <filename> - delete file\n");
|
||||
printf(" get <filename> - get file\n");
|
||||
printf(" set <filename> - set file\n");
|
||||
}
|
||||
|
||||
|
||||
static int
|
||||
parseOptions(int argc, char** argv)
|
||||
{
|
||||
int currentArgc = 1;
|
||||
|
||||
int retVal = 0;
|
||||
|
||||
while (currentArgc < argc) {
|
||||
if (strcmp(argv[currentArgc], "-h") == 0) {
|
||||
hostname = argv[++currentArgc];
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "-p") == 0) {
|
||||
tcpPort = atoi(argv[++currentArgc]);
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "del") == 0) {
|
||||
operation = FileOperationType_Del;
|
||||
filename = argv[++currentArgc];
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "dir") == 0) {
|
||||
operation = FileOperationType_Dir;
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "info") == 0) {
|
||||
operation = FileOperationType_Info;
|
||||
filename = argv[++currentArgc];
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "get") == 0) {
|
||||
operation = FileOperationType_Get;
|
||||
filename = argv[++currentArgc];
|
||||
}
|
||||
else if (strcmp(argv[currentArgc], "set") == 0) {
|
||||
operation = FileOperationType_Set;
|
||||
filename = argv[++currentArgc];
|
||||
}
|
||||
else {
|
||||
printf("Unknown operation!\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
currentArgc++;
|
||||
}
|
||||
|
||||
return retVal;
|
||||
}
|
||||
|
||||
void
|
||||
showDirectory(IedConnection con)
|
||||
{
|
||||
IedClientError error;
|
||||
|
||||
/* Get the root directory */
|
||||
LinkedList rootDirectory =
|
||||
IedConnection_getFileDirectory(con, &error, NULL);
|
||||
|
||||
if (error != IED_ERROR_OK) {
|
||||
printf("Error retrieving file directory\n");
|
||||
}
|
||||
else {
|
||||
LinkedList directoryEntry = LinkedList_getNext(rootDirectory);
|
||||
|
||||
while (directoryEntry != NULL) {
|
||||
|
||||
FileDirectoryEntry entry = (FileDirectoryEntry) directoryEntry->data;
|
||||
|
||||
printf("%s %i\n", FileDirectoryEntry_getFileName(entry), FileDirectoryEntry_getFileSize(entry));
|
||||
|
||||
directoryEntry = LinkedList_getNext(directoryEntry);
|
||||
}
|
||||
|
||||
LinkedList_destroyDeep(rootDirectory, (LinkedListValueDeleteFunction) FileDirectoryEntry_destroy);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
getFile(IedConnection con)
|
||||
{
|
||||
IedClientError error;
|
||||
|
||||
char* bname = strdup(filename);
|
||||
|
||||
char* localFilename = basename(bname);
|
||||
|
||||
FILE* fp = fopen(localFilename, "w");
|
||||
|
||||
if (fp != NULL) {
|
||||
|
||||
/* Download a file from the server */
|
||||
IedConnection_getFile(con, &error, filename, downloadHandler, (void*) fp);
|
||||
|
||||
if (error != IED_ERROR_OK)
|
||||
printf("Failed to get file!\n");
|
||||
|
||||
fclose(fp);
|
||||
}
|
||||
else
|
||||
printf("Failed to open file %s\n", localFilename);
|
||||
|
||||
free(bname);
|
||||
}
|
||||
|
||||
void
|
||||
setFile(IedConnection con)
|
||||
{
|
||||
IedClientError error;
|
||||
|
||||
char* dirc = strdup(filename);
|
||||
char* basec = strdup(filename);
|
||||
|
||||
char* localDirName = dirname(dirc);
|
||||
char* localFileName = basename(basec);
|
||||
|
||||
printf("local dir: %s\n", localDirName);
|
||||
printf("local file: %s\n", localFileName);
|
||||
|
||||
/* IedConnection_setFilestoreBasepath requires the file separator at the end! */
|
||||
strcpy(dirc, localDirName);
|
||||
strcat(dirc, "/");
|
||||
|
||||
printf("filestore basepath: %s\n", dirc);
|
||||
|
||||
IedConnection_setFilestoreBasepath(con, dirc);
|
||||
|
||||
IedConnection_setFile(con, &error, localFileName, localFileName);
|
||||
|
||||
if (error != IED_ERROR_OK)
|
||||
printf("Failed to set file! (code=%i)\n", error);
|
||||
|
||||
free(dirc);
|
||||
free(basec);
|
||||
}
|
||||
|
||||
void
|
||||
deleteFile(IedConnection con)
|
||||
{
|
||||
IedClientError error;
|
||||
|
||||
/* Delete file at server */
|
||||
IedConnection_deleteFile(con, &error, filename);
|
||||
|
||||
if (error != IED_ERROR_OK)
|
||||
printf("Failed to delete file! (code=%i)\n", error);
|
||||
}
|
||||
|
||||
int
|
||||
main(int argc, char** argv)
|
||||
{
|
||||
if (argc < 2) {
|
||||
printHelp();
|
||||
return 0;
|
||||
}
|
||||
|
||||
parseOptions(argc, argv);
|
||||
|
||||
if (operation == FileOperationType_None) {
|
||||
printHelp();
|
||||
return 0;
|
||||
}
|
||||
|
||||
IedClientError error;
|
||||
|
||||
IedConnection con = IedConnection_create();
|
||||
|
||||
IedConnection_connect(con, &error, hostname, tcpPort);
|
||||
|
||||
if (error == IED_ERROR_OK) {
|
||||
|
||||
|
||||
switch (operation) {
|
||||
case FileOperationType_Dir:
|
||||
showDirectory(con);
|
||||
break;
|
||||
case FileOperationType_Get:
|
||||
getFile(con);
|
||||
break;
|
||||
case FileOperationType_Del:
|
||||
deleteFile(con);
|
||||
break;
|
||||
case FileOperationType_Info:
|
||||
break;
|
||||
case FileOperationType_Set:
|
||||
setFile(con);
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
IedConnection_abort(con, &error);
|
||||
}
|
||||
else {
|
||||
printf("Failed to connect to %s:%i\n", hostname, tcpPort);
|
||||
}
|
||||
|
||||
IedConnection_destroy(con);
|
||||
}
|
||||
|
||||
|
|
@ -39,7 +39,7 @@ static MmsError
|
|||
fileAccessHandler (void* parameter, MmsServerConnection connection, MmsFileServiceType service,
|
||||
const char* localFilename, const char* otherFilename)
|
||||
{
|
||||
printf("fileAccessHanlder: service = %i, local-file: %s other-file: %s\n", service, localFilename, otherFilename);
|
||||
printf("fileAccessHandler: service = %i, local-file: %s other-file: %s\n", service, localFilename, otherFilename);
|
||||
|
||||
/* Don't allow client to rename files */
|
||||
if (service == MMS_FILE_ACCESS_TYPE_RENAME)
|
||||
|
|
Loading…
Add table
Reference in a new issue