//------------------------------------------------------------------------------ static tOplkError downloadNetConf(tCfmNodeInfo* pNodeInfo_p) { tOplkError ret = kErrorOk; if (pNodeInfo_p->cfmState == kCfmStateDownload) { const tIdentResponse* pIdentResponse = NULL; identu_getIdentResponse(pNodeInfo_p->eventCnProgress.nodeId, &pIdentResponse); if (pIdentResponse == NULL) { DEBUG_LVL_CFM_TRACE("CN%x Ident Response is NULL\n", pNodeInfo_p->eventCnProgress.nodeId); return kErrorInvalidNodeId; } if (ami_getUint32Le(&pIdentResponse->featureFlagsLe) & NMT_FEATUREFLAGS_CFM) { pNodeInfo_p->cfmState = kCfmStateDownloadNetConf; pNodeInfo_p->entriesRemaining = NMT_MAX_NODE_ID; pNodeInfo_p->eventCnProgress.objectIndex = 0x1F22; } } for (; pNodeInfo_p->entriesRemaining > 0; pNodeInfo_p->entriesRemaining--) { UINT subindex = NMT_MAX_NODE_ID - pNodeInfo_p->entriesRemaining + 1; tObdSize obdSize; const UINT8* pData; obdSize = obdu_getDataSize(0x1F22, subindex); // Download only cDCFs with at least one entry if (obdSize <= 4) continue; // fetch pointer to ConciseDCF from object 0x1F22 // (this allows the application to link its own memory to this object) pData = (const UINT8*)obdu_getObjectDataPtr(0x1F22, subindex); if (pData == NULL) return kErrorCfmNoConfigData; pNodeInfo_p->entriesRemaining--; pNodeInfo_p->eventCnProgress.objectSubIndex = subindex; ret = sdoWriteObject(pNodeInfo_p, pData, (UINT)obdSize); return ret; } if (pNodeInfo_p->entriesRemaining == 0) { // download finished ret = finishDownload(pNodeInfo_p); if (ret != kErrorOk) return ret; } return ret; }
void DownloadRequest::handle() { if (!_localFile) { warning("DownloadRequest: no file to write"); finishError(Networking::ErrorResponse(this, false, true, "", -1)); return; } if (!_localFile->isOpen()) { warning("DownloadRequest: failed to open file to write"); finishError(Networking::ErrorResponse(this, false, true, "", -1)); return; } if (!_remoteFileStream) { //waiting for callback return; } uint32 readBytes = _remoteFileStream->read(_buffer, DOWNLOAD_REQUEST_BUFFER_SIZE); if (readBytes != 0) if (_localFile->write(_buffer, readBytes) != readBytes) { warning("DownloadRequest: unable to write all received bytes into output file"); finishError(Networking::ErrorResponse(this, false, true, "", -1)); return; } if (_remoteFileStream->eos()) { if (_remoteFileStream->httpResponseCode() != 200) { warning("DownloadRequest: HTTP response code is not 200 OK (it's %ld)", _remoteFileStream->httpResponseCode()); //TODO: do something about it actually // the problem is file's already downloaded, stream is over // so we can't return error message anymore } finishDownload(_remoteFileStream->httpResponseCode() == 200); _localFile->close(); //yes, I know it's closed automatically in ~DumpFile() } }
void FolderDownloadRequest::downloadNextFile() { do { if (_pendingFiles.empty()) { sendCommand(GUI::kDownloadEndedCmd, 0); finishDownload(_failedFiles); return; } _currentFile = _pendingFiles.back(); _pendingFiles.pop_back(); } while (_currentFile.isDirectory()); // directories are actually removed earlier, in the directoryListedCallback() sendCommand(GUI::kDownloadProgressCmd, (int)(getProgress() * 100)); Common::String remotePath = _currentFile.path(); Common::String localPath = remotePath; if (_remoteDirectoryPath == "" || remotePath.hasPrefix(_remoteDirectoryPath)) { localPath.erase(0, _remoteDirectoryPath.size()); if (_remoteDirectoryPath != "" && (_remoteDirectoryPath.lastChar() != '/' && _remoteDirectoryPath.lastChar() != '\\')) localPath.erase(0, 1); } else { warning("FolderDownloadRequest: Can't process the following paths:"); warning("remote directory: %s", _remoteDirectoryPath.c_str()); warning("remote file under that directory: %s", remotePath.c_str()); } if (_localDirectoryPath != "") { if (_localDirectoryPath.lastChar() == '/' || _localDirectoryPath.lastChar() == '\\') localPath = _localDirectoryPath + localPath; else localPath = _localDirectoryPath + "/" + localPath; } debug(9, "FolderDownloadRequest: %s -> %s", remotePath.c_str(), localPath.c_str()); _workingRequest = _storage->downloadById( _currentFile.id(), localPath, new Common::Callback<FolderDownloadRequest, Storage::BoolResponse>(this, &FolderDownloadRequest::fileDownloadedCallback), new Common::Callback<FolderDownloadRequest, Networking::ErrorResponse>(this, &FolderDownloadRequest::fileDownloadedErrorCallback) ); }
//------------------------------------------------------------------------------ static tOplkError downloadObject(tCfmNodeInfo* pNodeInfo_p) { tOplkError ret = kErrorOk; // forward data pointer for last transfer pNodeInfo_p->pDataConciseDcf += pNodeInfo_p->curDataSize; pNodeInfo_p->bytesRemaining -= pNodeInfo_p->curDataSize; if (pNodeInfo_p->entriesRemaining > 0) { if (pNodeInfo_p->bytesRemaining < CDC_OFFSET_DATA) { // not enough bytes left in ConciseDCF pNodeInfo_p->eventCnProgress.error = kErrorCfmInvalidDcf; ret = callCbProgress(pNodeInfo_p); if (ret != kErrorOk) return ret; return finishConfig(pNodeInfo_p, kNmtNodeCommandConfErr); } // fetch next item from ConciseDCF pNodeInfo_p->eventCnProgress.objectIndex = ami_getUint16Le(&pNodeInfo_p->pDataConciseDcf[CDC_OFFSET_INDEX]); pNodeInfo_p->eventCnProgress.objectSubIndex = ami_getUint8Le(&pNodeInfo_p->pDataConciseDcf[CDC_OFFSET_SUBINDEX]); pNodeInfo_p->curDataSize = (UINT)ami_getUint32Le(&pNodeInfo_p->pDataConciseDcf[CDC_OFFSET_SIZE]); pNodeInfo_p->pDataConciseDcf += CDC_OFFSET_DATA; pNodeInfo_p->bytesRemaining -= CDC_OFFSET_DATA; pNodeInfo_p->eventCnProgress.bytesDownloaded += CDC_OFFSET_DATA; if ((pNodeInfo_p->bytesRemaining < pNodeInfo_p->curDataSize) || (pNodeInfo_p->curDataSize == 0)) { // not enough bytes left in ConciseDCF pNodeInfo_p->eventCnProgress.error = kErrorCfmInvalidDcf; ret = callCbProgress(pNodeInfo_p); if (ret != kErrorOk) return ret; return finishConfig(pNodeInfo_p, kNmtNodeCommandConfErr); } pNodeInfo_p->entriesRemaining--; ret = sdoWriteObject(pNodeInfo_p, pNodeInfo_p->pDataConciseDcf, pNodeInfo_p->curDataSize); if (ret != kErrorOk) return ret; } else { // download finished #if defined(CONFIG_INCLUDE_NMT_RMN) ret = downloadNetConf(pNodeInfo_p); #else ret = finishDownload(pNodeInfo_p); #endif if (ret != kErrorOk) return ret; } return ret; }