最近老板突然说, 需要在原先的相机系统上面添加一个文件传输的模块, 不让用现成的软件如filezilla, 没办法只能自己手写一个
这个部分主要涉及:
1. 文件存在性检测 (使用fileInfo 进行存在性检测), 参考文章: http://blog.csdn.net/arrowzz/article/details/17144497
2. ip 地址有效性检测(正则表达式检测) 参考文章: http://blog.csdn.net/fengqingtao2008/article/details/7344906
3. 调用 C++ 的 dll 模块 参考文章: http://blog.csdn.net/zhyh1435589631/article/details/52181093
Imports System.Text.RegularExpressions
Imports System.IO
Public Class Form1
Private Declare Function myclient Lib "dll_client2.dll" (ByVal port As Integer, ByVal filename As String, ByVal ip As String) As Integer
Private Sub Button1_Click(sender As Object, e As EventArgs) Handles Button1.Click
// 文件存在性检测
Dim file As String = FileName.Text.ToString()
If Not checkFile(file) Then
MessageBox.Show("文件不存在,请重试")
Return
End If
// ip 有效性检测
Dim ip As String = IPADDR.Text.ToString.Trim
If ip = "" Then
ip = "127.0.0.1"
End If
If Not checkIP(ip) Then
MessageBox.Show("IP地址错误,请重试")
Return
End If
// 调用 C++ dll 模块实现文件传输
Dim ret As Integer = myclient(6000, file, ip)
If ret <> 0 Then
MessageBox.Show("传输失败,请重试")
Else
MessageBox.Show("传输成功")
End If
End Sub
// 支持拖拽
Private Sub FileName_DragDrop(sender As Object, e As DragEventArgs) Handles FileName.DragDrop
Dim MyFiles() As String
MyFiles = e.Data.GetData(DataFormats.FileDrop)
FileName.Text = MyFiles(0)
End Sub
Private Sub FileName_DragEnter(sender As Object, e As DragEventArgs) Handles FileName.DragEnter
e.Effect = DragDropEffects.All
End Sub
Private Function checkIP(ip As String)
Dim strPattern As String = "^(\d{1,2}|1\d\d|2[0-4]\d|25[0-5]).(\d{1,2}|1\d\d|2[0-4]\d|25[0-5]).(\d{1,2}|1\d\d|2[0-4]\d|25[0-5]).(\d{1,2}|1\d\d|2[0-4]\d|25[0-5])$"
Return Regex.IsMatch(ip, strPattern)
End Function
Private Function checkFile(file As String)
Dim fFile As New FileInfo(file)
If Not fFile.Exists Then
Return False
Else
Return True
End If
End Function
End Class
client.def
LIBRARY
EXPORTS
myclient = ?myclient@@YGHHPAD0@Z
client.h
#pragma once
int __stdcall myclient(int port, char * filename1, char * ip);
client.cpp
#include <WinSock2.h>
#include <stdio.h>
#include <fstream>
#include <string>
#include <thread>
#include <iostream>
#include "client.h"
using namespace std;
#pragma comment(lib, "ws2_32.lib")
const int bufsize = 1024;
int __stdcall myclient(int port, char * filename1, char * ip){
string tmp(filename1);
int pos = tmp.rfind('\\');
if (pos >= 0){
tmp = tmp.substr(pos + 1);
}
char filename_buf[255] = { 0 };
strcpy(filename_buf, tmp.c_str());
WORD wVersionRequested;
WSADATA wsaData;
int err;
wVersionRequested = MAKEWORD(1, 1);
err = WSAStartup(wVersionRequested, &wsaData);
if (err != 0)
return -1;
if (LOBYTE(wsaData.wVersion) != 1 || HIBYTE(wsaData.wVersion) != 1){
WSACleanup();
return -1;
}
SOCKET sockClient = socket(AF_INET, SOCK_STREAM, 0);
SOCKADDR_IN addrSrv;
addrSrv.sin_addr.S_un.S_addr = inet_addr(ip);
addrSrv.sin_family = AF_INET;
addrSrv.sin_port = htons(port);
int ret = connect(sockClient, (SOCKADDR*)&addrSrv, sizeof(SOCKADDR));
// send filename
ret = send(sockClient, filename_buf, strlen(filename_buf) + 1, 0);
if (ret == -1){
cerr << "error" << endl;
return -1;
}
// send content
#define _CPP
#ifdef _CPP
string filename(filename1);
ifstream fd(filename, ifstream::binary);
fd.seekg(0, ifstream::end);
// size
Sleep(100);
char buf[bufsize] = { 0 };
int filesize = fd.tellg();
sprintf(buf, "%d", filesize);
send(sockClient, buf, strlen(buf) + 1, 0);
fd.seekg(0);
memset(buf, 0, bufsize);
Sleep(500);
while (fd.good()){
fd.read(buf, bufsize);
int count = fd.gcount();
ret = send(sockClient, buf, count, 0);
if (ret == -1){
cerr << "error" << endl;
return -1;
}
memset(buf, 0, bufsize);
}
cout << buf << endl;
#else
FILE * fd = fopen(filename_buf, "rb");
Sleep(500);
char buf[bufsize] = { 0 };
while (true){
int count = fread(buf, 1, bufsize, fd);
if (count <= 0)
break;
ret = send(sockClient, buf, count, 0);
if (ret == -1){
cerr << "error" << endl;
return -1;
}
memset(buf, 0, bufsize);
}
fclose(fd);
#endif
return 0;
}
#include <WinSock2.h>
#include <stdio.h>
#include <fstream>
#include <string>
#include <thread>
//using namespace std;
using std::ofstream;
using std::string;
using std::thread;
#pragma comment(lib, "ws2_32.lib")
const int bufsize = 1024;
int myrecv(SOCKET sockConn){
char buffer[bufsize] = { 0 };
// filename
int ret = recv(sockConn, buffer, bufsize, 0);
if (ret == -1){
return -1;
}
#define _CPP
#ifdef _CPP
string filename(buffer);
recv(sockConn, buffer, bufsize, 0);
int count = atoi(buffer);
ofstream of(filename, ofstream::binary);
memset(buffer, 0, bufsize);
int sum = 0;
while ((ret = recv(sockConn, buffer, bufsize, 0)) > 0){
of.write(buffer, ret);
sum += ret;
memset(buffer, 0, bufsize);
if (sum >= count)
break;
}
#else
FILE * fd = fopen(buffer, "wb");
memset(buffer, 0, bufsize);
while ((ret = recv(sockConn, buffer, bufsize, 0)) > 0){
fwrite(buffer, 1, ret, fd);
memset(buffer, 0, bufsize);
}
fclose(fd);
#endif
return 0;
}
int main(int argc, char * argv[]){
int port = 6000;
if (argc == 2){
port = atoi(argv[1]);
}
WORD wVersionRequested;
WSADATA wsaData;
int err;
wVersionRequested = MAKEWORD(1, 1);
err = WSAStartup(wVersionRequested, &wsaData);
if (err != 0)
return -1;
if (LOBYTE(wsaData.wVersion) != 1 || HIBYTE(wsaData.wVersion) != 1){
WSACleanup();
return -1;
}
SOCKET sockSrv = socket(AF_INET, SOCK_STREAM, 0);
SOCKADDR_IN addrSrv;
addrSrv.sin_addr.S_un.S_addr = htonl(INADDR_ANY);
addrSrv.sin_family = AF_INET;
addrSrv.sin_port = htons(port);
bind(sockSrv, (SOCKADDR *)&addrSrv, sizeof(SOCKADDR));
listen(sockSrv, 5);
SOCKADDR_IN addrClient;
int len = sizeof(SOCKADDR);
while (true){
SOCKET sockConn = accept(sockSrv, (SOCKADDR *)&addrClient, &len);
thread t1(myrecv, sockConn);
t1.join();
/*myrecv(sockConn);*/
}
return 0;
}