Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Q
qgroundcontrol
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Valentin Platzgummer
qgroundcontrol
Commits
e9f6640d
Commit
e9f6640d
authored
Mar 13, 2015
by
crashmatt
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
mavlink-ftp - Initial code structure for write file support
parent
8295b8dc
Changes
2
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
165 additions
and
2 deletions
+165
-2
QGCUASFileManager.cc
src/uas/QGCUASFileManager.cc
+143
-0
QGCUASFileManager.h
src/uas/QGCUASFileManager.h
+22
-2
No files found.
src/uas/QGCUASFileManager.cc
View file @
e9f6640d
...
...
@@ -199,6 +199,94 @@ void QGCUASFileManager::_listAckResponse(Request* listAck)
}
}
/// @brief Respond to the Ack associated with the create command.
void
QGCUASFileManager
::
_createAckResponse
(
Request
*
createAck
)
{
_currentOperation
=
kCOWrite
;
_activeSession
=
createAck
->
hdr
.
session
;
// File length comes back in data. Compare with
Q_ASSERT
(
createAck
->
hdr
.
size
==
sizeof
(
uint32_t
));
// Start the sequence of read commands
_writeOffset
=
0
;
// Start writing at beginning of file
_writeSize
=
0
;
_writeFileDatablock
();
}
/// @brief Respond to the Ack associated with the write command.
void
QGCUASFileManager
::
_writeAckResponse
(
Request
*
writeAck
)
{
if
(
writeAck
->
hdr
.
session
!=
_activeSession
)
{
_currentOperation
=
kCOIdle
;
_writeFileAccumulator
.
clear
();
_emitErrorMessage
(
tr
(
"Write: Incorrect session returned"
));
return
;
}
if
(
writeAck
->
hdr
.
offset
!=
_writeOffset
)
{
_currentOperation
=
kCOIdle
;
_writeFileAccumulator
.
clear
();
_emitErrorMessage
(
tr
(
"Write: Offset returned (%1) differs from offset requested (%2)"
).
arg
(
writeAck
->
hdr
.
offset
).
arg
(
_writeOffset
));
return
;
}
if
(
writeAck
->
hdr
.
size
!=
_writeSize
)
{
_currentOperation
=
kCOIdle
;
_writeFileAccumulator
.
clear
();
_emitErrorMessage
(
tr
(
"Write: Offset returned (%1) differs from offset requested (%2)"
).
arg
(
writeAck
->
hdr
.
offset
).
arg
(
_writeOffset
));
return
;
}
if
(
writeAck
->
hdr
.
size
!=
_writeFileSize
){
_currentOperation
=
kCOIdle
;
_writeFileAccumulator
.
clear
();
_emitErrorMessage
(
tr
(
"Write: Size returned (%1) differs from size requested (%2)"
).
arg
(
writeAck
->
hdr
.
size
).
arg
(
_writeSize
));
return
;
}
_writeFileDatablock
();
}
/// @brief Send next write file data block.
void
QGCUASFileManager
::
_writeFileDatablock
(
void
)
{
/// @brief Maximum data size in RequestHeader::data
// static const uint8_t kMaxDataLength = MAVLINK_MSG_FILE_TRANSFER_PROTOCOL_FIELD_PAYLOAD_LEN - sizeof(RequestHeader);
// static const uint8_t kMaxDataLength = Request.data;
if
(
_writeOffset
+
_writeSize
>=
_writeFileSize
){
_currentOperation
=
kCOIdle
;
_writeFileAccumulator
.
clear
();
emit
uploadFileComplete
();
}
Request
request
;
request
.
hdr
.
session
=
_activeSession
;
request
.
hdr
.
opcode
=
kCmdWriteFile
;
request
.
hdr
.
offset
=
_writeOffset
;
_writeOffset
+=
_writeSize
;
if
(
_writeOffset
+
sizeof
(
request
.
data
)
<
_writeFileSize
)
_writeSize
=
sizeof
(
request
.
data
);
else
_writeSize
=
_writeFileSize
-
_writeOffset
-
1
;
request
.
hdr
.
size
=
_writeSize
;
// memcpy this? _writeFileAccumulator.mid(_writeOffset, _writeSize), _writeSize);
for
(
uint32_t
index
=
_writeOffset
;
index
<
_writeOffset
+
_writeSize
;
index
++
)
request
.
data
[
index
]
=
_writeFileAccumulator
.
at
(
index
);
_sendRequest
(
&
request
);
}
void
QGCUASFileManager
::
receiveMessage
(
LinkInterface
*
link
,
mavlink_message_t
message
)
{
Q_UNUSED
(
link
);
...
...
@@ -259,6 +347,14 @@ void QGCUASFileManager::receiveMessage(LinkInterface* link, mavlink_message_t me
_readAckResponse
(
request
);
break
;
case
kCOCreate
:
_createAckResponse
(
request
);
break
;
case
kCOWrite
:
_writeAckResponse
(
request
);
break
;
default:
_emitErrorMessage
(
tr
(
"Ack received in unexpected state"
));
break
;
...
...
@@ -365,6 +461,47 @@ void QGCUASFileManager::downloadPath(const QString& from, const QDir& downloadDi
_sendRequest
(
&
request
);
}
/// @brief Uploads the specified file.
/// @param toPath File in UAS to upload to, fully qualified path
/// @param uploadFile Local file to upload from
void
QGCUASFileManager
::
uploadPath
(
const
QString
&
toPath
,
const
QFileInfo
&
uploadFile
)
{
if
(
toPath
.
isEmpty
())
{
return
;
}
if
(
not
uploadFile
.
isReadable
()){
_emitErrorMessage
(
tr
(
"File (%1) is not readable for upload"
).
arg
(
uploadFile
.
path
()));
}
QFile
file
(
uploadFile
.
absoluteFilePath
());
if
(
!
file
.
open
(
QIODevice
::
ReadOnly
|
QIODevice
::
Truncate
))
{
_emitErrorMessage
(
tr
(
"Unable to open local file for upload (%1)"
).
arg
(
uploadFile
.
absoluteFilePath
()));
return
;
}
_writeFileAccumulator
=
file
.
readAll
();
qint64
bytesRead
=
file
.
write
((
const
char
*
)
_readFileAccumulator
,
_readFileAccumulator
.
length
());
if
(
bytesRead
<=
0
)
{
file
.
close
();
_emitErrorMessage
(
tr
(
"Unable to read data from local file (%1)"
).
arg
(
uploadFile
.
absoluteFilePath
()));
return
;
}
_currentOperation
=
kCOCreate
;
Request
request
;
request
.
hdr
.
session
=
0
;
request
.
hdr
.
opcode
=
kCmdCreateFile
;
request
.
hdr
.
offset
=
0
;
request
.
hdr
.
size
=
bytesRead
;
_fillRequestWithString
(
&
request
,
toPath
);
_sendRequest
(
&
request
);
}
QString
QGCUASFileManager
::
errorString
(
uint8_t
errorCode
)
{
switch
(
errorCode
)
{
...
...
@@ -441,6 +578,12 @@ void QGCUASFileManager::_ackTimeout(void)
_emitErrorMessage
(
tr
(
"Timeout waiting for ack: Sending Terminate command"
));
_sendTerminateCommand
();
break
;
case
kCOCreate
:
case
kCOWrite
:
_currentOperation
=
kCOAck
;
_emitErrorMessage
(
tr
(
"Timeout waiting for ack: Sending Terminate command"
));
_sendTerminateCommand
();
break
;
default:
_currentOperation
=
kCOIdle
;
_emitErrorMessage
(
tr
(
"Timeout waiting for ack"
));
...
...
src/uas/QGCUASFileManager.h
View file @
e9f6640d
...
...
@@ -68,10 +68,21 @@ signals:
/// @brief Signaled to indicate completion of file download. If an error occurs during download this signal will not be emitted.
void
downloadFileComplete
(
void
);
/// @brief Signalled after createFile acknowledge is returned to indicate length of file being downloaded
void
uploadFileLength
(
unsigned
int
length
);
/// @brief Signalled during file upload to indicate progress
/// @param bytesReceived Number of bytes currently transmitted to file
void
uploadFileProgress
(
unsigned
int
bytesReceived
);
/// @brief Signaled to indicate completion of file upload. If an error occurs during download this signal will not be emitted.
void
uploadFileComplete
(
void
);
public
slots
:
void
receiveMessage
(
LinkInterface
*
link
,
mavlink_message_t
message
);
void
listDirectory
(
const
QString
&
dirPath
);
void
downloadPath
(
const
QString
&
from
,
const
QDir
&
downloadDir
);
void
uploadPath
(
const
QString
&
toPath
,
const
QFileInfo
&
uploadFile
);
protected:
...
...
@@ -144,6 +155,8 @@ protected:
kCOList
,
// waiting for List response
kCOOpen
,
// waiting for Open response
kCORead
,
// waiting for Read response
kCOCreate
,
// waiting for Create response
kCOWrite
,
// waiting for Write response
};
...
...
@@ -161,6 +174,9 @@ protected:
void
_openAckResponse
(
Request
*
openAck
);
void
_readAckResponse
(
Request
*
readAck
);
void
_listAckResponse
(
Request
*
listAck
);
void
_createAckResponse
(
Request
*
createAck
);
void
_writeAckResponse
(
Request
*
writeAck
);
void
_writeFileDatablock
(
void
);
void
_sendListCommand
(
void
);
void
_sendTerminateCommand
(
void
);
void
_closeReadSession
(
bool
success
);
...
...
@@ -179,7 +195,11 @@ protected:
uint8_t
_activeSession
;
///< currently active session, 0 for none
uint32_t
_readOffset
;
///< current read offset
uint32_t
_writeOffset
;
///< current write offset
uint32_t
_writeSize
;
///< current write data size
uint32_t
_writeFileSize
;
///< current write file size
QByteArray
_readFileAccumulator
;
///< Holds file being downloaded
QByteArray
_writeFileAccumulator
;
///< Holds file being uploaded
QDir
_readFileDownloadDir
;
///< Directory to download file to
QString
_readFileDownloadFilename
;
///< Filename (no path) for download file
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment