blob: 6f444e9bd5c7fb8ca3569eb50ccc3bb87ba26f3a [file] [log] [blame]
Constantin Kaplinsky4a1f6952006-05-19 10:09:44 +00001/* Copyright (C) 2006 TightVNC Team. All Rights Reserved.
2 *
3 * Developed by Dennis Syrovatsky
4 *
5 * This is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This software is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this software; if not, write to the Free Software
17 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
18 * USA.
19 *
20 * TightVNC distribution homepage on the Web: http://www.tightvnc.com/
21 *
22 */
23
24// -=- SFileTransfer.cxx
25
26#include <rfb/msgTypes.h>
27#include <rfb/SFileTransfer.h>
28
29using namespace rfb;
30
31SFileTransfer::SFileTransfer(network::Socket *sock) :
Constantin Kaplinsky21882422006-05-19 11:13:04 +000032 m_bUploadStarted(false), m_bDownloadStarted(false),
33 m_reader(&sock->inStream()), m_writer(&sock->outStream()), m_pSocket(sock)
Constantin Kaplinsky4a1f6952006-05-19 10:09:44 +000034{
35}
36
37SFileTransfer::~SFileTransfer()
38{
39}
40
41bool
42SFileTransfer::processMessages(int type)
43{
44 switch(type)
45 {
46 case msgTypeFileListRequest:
47 return processFileListRequest();
48 case msgTypeFileDownloadRequest:
49 return processFileDownloadRequest();
50 case msgTypeFileUploadRequest:
51 return processFileUploadRequest();
52 case msgTypeFileUploadData:
53 return processFileUploadData();
54 case msgTypeFileDownloadCancel:
55 return processFileDownloadCancel();
56 case msgTypeFileUploadFailed:
57 return processFileUploadFailed();
58 case msgTypeFileCreateDirRequest:
59 return processFileCreateDirRequest();
60 case msgTypeFileDirSizeRequest:
61 return processFileDirSizeRequest();
62 case msgTypeFileRenameRequest:
63 return processFileRenameRequest();
64 case msgTypeFileDeleteRequest:
65 return processFileDeleteRequest();
66 default:
67 return false;
68 }
69}
70
71bool
72SFileTransfer::processFileListRequest()
73{
74 char szDirName[FT_FILENAME_SIZE] = {0};
75 unsigned int dirNameSize = FT_FILENAME_SIZE;
76 unsigned int flags = 0;
77
78 if (!m_reader.readFileListRqst(&dirNameSize, szDirName, &flags)) return false;
79
80 if (!convertPathFromNet(szDirName)) return false;
81
82 bool bDirOnly = false;
83 if (flags & 0x10) bDirOnly = true;
84
85 FileInfo fi;
Dennis Syrovatskyf04f7eb2006-05-22 08:14:52 +000086 if (!makeFileList(szDirName, &fi, bDirOnly)) {
87 flags = (flags | 0x80);
88 }
Constantin Kaplinsky4a1f6952006-05-19 10:09:44 +000089 return m_writer.writeFileListData((unsigned char)flags, &fi);
90}
91
92bool
93SFileTransfer::processFileDownloadRequest()
94{
95 char szName[FT_FILENAME_SIZE] = {0};
96 unsigned int nameSize = FT_FILENAME_SIZE;
97 unsigned int position = 0;
98
99 if (!m_reader.readFileDownloadRqst(&nameSize, szName, &position)) return false;
100
101 if (!convertPathFromNet(szName)) return false;
102
103 if (m_bDownloadStarted) {
104 char reason[] = "The download is already started";
105 m_writer.writeFileLastRqstFailed(msgTypeFileDownloadRequest, strlen(reason), reason);
106 return false;
107 }
108
109 if (!m_fileReader.create(szName)) return false;
110
111 m_bDownloadStarted = true;
112
113 sendFileDownloadPortion();
114
115 return true;
116}
117
118bool
119SFileTransfer::sendFileDownloadPortion()
120{
121 char buffer[FT_MAX_SENDING_SIZE];
122 unsigned int bytesRead = 0;
123
124 if (m_fileReader.read((void *)buffer, FT_MAX_SENDING_SIZE, &bytesRead)) {
125 if (bytesRead == 0) {
126 m_writer.writeFileDownloadData(m_fileReader.getTime());
127 m_fileReader.close();
128 m_bDownloadStarted = false;
129 return true;
130 } else {
131 m_writer.writeFileDownloadData(bytesRead, buffer);
132 return initDownloadCallback();
133 }
134 } else {
135 char reason[] = "Error while reading from file";
136 m_writer.writeFileDownloadFailed(strlen(reason), reason);
137 m_fileReader.close();
138 m_bDownloadStarted = false;
139 return true;
140 }
141}
142
143bool
144SFileTransfer::processFileUploadRequest()
145{
146 char szName[FT_FILENAME_SIZE] = {0};
147 unsigned int nameSize = FT_FILENAME_SIZE;
148 unsigned int position = 0;
149
150 if (!m_reader.readFileUploadRqst(&nameSize, szName, &position)) return false;
151
152 if (!convertPathFromNet(szName)) return false;
153
154 if (m_bUploadStarted) {
155 char reason[] = "The upload is already started";
156 m_writer.writeFileLastRqstFailed(msgTypeFileUploadRequest, strlen(reason), reason);
157 return false;
158 }
159
160 if (!m_fileWriter.create(szName)) {
161 char reason[] = "Can't create local file";
162 m_writer.writeFileLastRqstFailed(msgTypeFileUploadRequest, strlen(reason), reason);
163 return true;
164 }
165
166 m_bUploadStarted = true;
167
168 return true;
169}
170
171bool
172SFileTransfer::processFileUploadData()
173{
174 unsigned int dataSize = 0;
175 unsigned int modTime = 0;
176
177 void *pUploadData = m_reader.readFileUploadData(&dataSize, &modTime);
178
179 if (!m_bUploadStarted) {
180 char reason[] = "Upload is impossible";
181 m_writer.writeFileUploadCancel(strlen(reason), reason);
182 } else {
183 if (pUploadData == NULL) {
184 if (modTime == 0) {
185 char reason[] = "Upload failed";
186 m_writer.writeFileUploadCancel(strlen(reason), reason);
187 } else {
188 m_fileWriter.setTime(modTime);
189 }
190 m_fileWriter.close();
191 m_bUploadStarted = false;
192 } else {
193 unsigned int dataWritten = 0;
194 m_fileWriter.write(pUploadData, dataSize, &dataWritten);
195 if (dataWritten != dataSize) {
196 char reason[] = "Upload failed";
197 m_writer.writeFileUploadCancel(strlen(reason), reason);
198 m_fileWriter.close();
199 m_bUploadStarted = false;
200 }
201 }
202 }
Constantin Kaplinskyade6bde2006-05-19 10:58:37 +0000203 // FIXME: For the next line, gcc says:
204 // warning: deleting `void *' is undefined
205 // Perhaps it should not be `void *' at all.
Constantin Kaplinsky4a1f6952006-05-19 10:09:44 +0000206 delete [] pUploadData;
207 return true;
208}
209
210bool
211SFileTransfer::processFileDownloadCancel()
212{
213 char szReason[FT_FILENAME_SIZE] = {0};
214 unsigned int reasonSize = FT_FILENAME_SIZE;
215
216 if (!m_reader.readFileDownloadCancel(&reasonSize, szReason)) return false;
217
218 m_fileReader.close();
219 m_bDownloadStarted = false;
220 return true;
221}
222
223bool
224SFileTransfer::processFileUploadFailed()
225{
226 char szReason[FT_FILENAME_SIZE] = {0};
227 unsigned int reasonSize = FT_FILENAME_SIZE;
228
229 if (!m_reader.readFileUploadFailed(&reasonSize, szReason)) return false;
230
231 deleteIt(m_fileWriter.getFilename());
232 m_fileWriter.close();
233 m_bUploadStarted = false;
234 return true;
235}
236
237bool
238SFileTransfer::processFileCreateDirRequest()
239{
240 char szName[FT_FILENAME_SIZE] = {0};
241 unsigned int nameSize = FT_FILENAME_SIZE;
242
243 if (!m_reader.readFileCreateDirRqst(&nameSize, szName)) return false;
244
245 if (!convertPathFromNet(szName)) return false;
246
247 return createDir(szName);
248}
249
250bool
251SFileTransfer::processFileDirSizeRequest()
252{
253 char szName[FT_FILENAME_SIZE] = {0};
254 unsigned int nameSize = FT_FILENAME_SIZE;
255
256 if (!m_reader.readFileDirSizeRqst(&nameSize, szName)) return false;
257
258 if (!convertPathFromNet(szName)) return false;
259
260 unsigned short highSize16 = 0;
261 unsigned int lowSize32 = 0;
262
263 if (!getDirSize(szName, &highSize16, &lowSize32)) return false;
264
265 return m_writer.writeFileDirSizeData(lowSize32, highSize16);
266}
267
268bool
269SFileTransfer::processFileRenameRequest()
270{
271 char szOldName[FT_FILENAME_SIZE] = {0};
272 char szNewName[FT_FILENAME_SIZE] = {0};
273
274 unsigned int oldNameSize = FT_FILENAME_SIZE;
275 unsigned int newNameSize = FT_FILENAME_SIZE;
276
277 if (!m_reader.readFileRenameRqst(&oldNameSize, &newNameSize, szOldName, szNewName)) return false;
278
279 if ((!convertPathFromNet(szOldName)) || (!convertPathFromNet(szNewName))) return false;
280
281 return renameIt(szOldName, szNewName);
282}
283
284bool
285SFileTransfer::processFileDeleteRequest()
286{
287 char szName[FT_FILENAME_SIZE] = {0};
288 unsigned int nameSize = FT_FILENAME_SIZE;
289
290 if (!m_reader.readFileDeleteRqst(&nameSize, szName)) return false;
291
292 if (!convertPathFromNet(szName)) return false;
293
294 return deleteIt(szName);
295}
296
297bool
298SFileTransfer::convertPathFromNet(char *pszPath)
299{
300 return true;
301}
302
303bool
304SFileTransfer::makeFileList(char *pszPath, FileInfo *pFI, bool bDirOnly)
305{
306 return false;
307}
308
309bool
310SFileTransfer::deleteIt(char *pszPath)
311{
312 return false;
313}
314
315bool
316SFileTransfer::renameIt(char *pszOldPath, char *pszNewPath)
317{
318 return false;
319}
320
321bool
322SFileTransfer::createDir(char *pszPath)
323{
324 return false;
325}
326
327bool
328SFileTransfer::getDirSize(char *pszName, unsigned short *pHighSize16,
329 unsigned int *pLowSize32)
330{
331 return false;
332}
333
334bool
335SFileTransfer::initDownloadCallback()
336{
337 return false;
338}