Home | History | Annotate | Download | only in src
      1 /* ------------------------------------------------------------------
      2  * Copyright (C) 1998-2009 PacketVideo
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either
     13  * express or implied.
     14  * See the License for the specific language governing permissions
     15  * and limitations under the License.
     16  * -------------------------------------------------------------------
     17  */
     18 #ifndef PVMF_PROTOCOLENGINE_PROGRESSIVE_DOWNLOAD_H_INCLUDED
     19 #define PVMF_PROTOCOLENGINE_PROGRESSIVE_DOWNLOAD_H_INCLUDED
     20 
     21 #ifndef PVMF_PROTOCOLENGINE_DOWNLOAD_COMMON_H_INCLUDED
     22 #include "pvmf_protocol_engine_download_common.h"
     23 #endif
     24 
     25 #define DEFAULT_STATE_NUMBER_FOR_DOWNLOAD_GET_REQUEST 1 // for progressive streaming or shoutcast
     26 
     27 
     28 class ProgressiveDownloadState_HEAD : public DownloadState
     29 {
     30     public:
     31         bool isCurrentStateOptional()
     32         {
     33             return true;
     34         }
     35 
     36     private:
     37         // To compose a request, the only difference is HEAD method
     38         OSCL_IMPORT_REF void setRequestBasics();
     39         OSCL_IMPORT_REF bool setHeaderFields();
     40         OSCL_IMPORT_REF int32 checkParsingStatus(int32 parsingStatus);
     41         int32 updateDownloadStatistics()
     42         {
     43             return 0;
     44         }
     45 
     46         // From HttpParsingBasicObjectObserver
     47         OSCL_IMPORT_REF int32 OutputDataAvailable(OUTPUT_DATA_QUEUE *aOutputQueue, const bool isHttpHeader);
     48 };
     49 
     50 class ProgressiveDownloadState_GET : public DownloadState
     51 {
     52     public:
     53         ProgressiveDownloadState_GET() : iSendEndOfMessageTruncate(false), iRangeHeaderSupported(true)
     54         {
     55             ;
     56         }
     57         // virtual destructor, let internal objects destruct automatically
     58         virtual ~ProgressiveDownloadState_GET()
     59         {
     60             iOutputDataQueue.clear();
     61         }
     62 
     63         void stop(const bool isAfterEOS = false)
     64         {
     65             OSCL_UNUSED_ARG(isAfterEOS);
     66             reset();
     67             sendRequest();
     68         }
     69 
     70         void reset()
     71         {
     72             iSendEndOfMessageTruncate = false;
     73             DownloadState::reset();
     74         }
     75 
     76     protected:
     77         OSCL_IMPORT_REF int32 processMicroStateGetResponsePreCheck();
     78         OSCL_IMPORT_REF virtual bool setHeaderFields();
     79         OSCL_IMPORT_REF bool setRangeHeaderFields();
     80         // From HttpParsingBasicObjectObserver
     81         OSCL_IMPORT_REF int32 OutputDataAvailable(OUTPUT_DATA_QUEUE *aOutputQueue, const bool isHttpHeader);
     82         OSCL_IMPORT_REF void updateOutputDataQueue(OUTPUT_DATA_QUEUE *aOutputQueue);
     83         bool isDownloadStreamingDoneState()
     84         {
     85             return true;
     86         }
     87         bool isLastState()
     88         {
     89             return true;
     90         }
     91         OSCL_IMPORT_REF void getStartFragmentInNewDownloadData(OUTPUT_DATA_QUEUE &aOutputQueue,
     92                 bool &aUseAllNewDownloadData,
     93                 uint32 &aStartFragsNo,
     94                 uint32 &aStartFragOffset);
     95         OSCL_IMPORT_REF void getEndFragmentInNewDownloadData(OUTPUT_DATA_QUEUE &aOutputQueue,
     96                 uint32 &aEndFragNo,
     97                 uint32 &aEndFragValidLen);
     98         OSCL_IMPORT_REF int32 checkContentInfoMatchingForResumeDownload();
     99         OSCL_IMPORT_REF virtual int32 checkParsingStatus(int32 parsingStatus);
    100         OSCL_IMPORT_REF int32 updateDownloadStatistics();
    101 
    102     protected:
    103         bool iSendEndOfMessageTruncate;
    104         bool iRangeHeaderSupported;
    105 };
    106 
    107 // Progressive Streaming is a special form of progressive download
    108 class ProgressiveStreamingState_GET : public ProgressiveDownloadState_GET
    109 {
    110     public:
    111         virtual void seek(const uint32 aSeekPosition)
    112         {
    113             iCfgFile->SetCurrentFileSize(aSeekPosition);
    114             iNeedGetResponsePreCheck = true; // reset the parser
    115         }
    116 
    117     protected:
    118         OSCL_IMPORT_REF int32 checkParsingStatus(int32 parsingStatus);
    119         void saveConfig()
    120         {
    121             ;
    122         }
    123 };
    124 
    125 // Http progressive download, do state transition
    126 class ProgressiveDownload : public HttpBasedProtocol
    127 {
    128     public:
    129         // create states of state machine
    130         ProgressiveDownload()
    131         {
    132             iState[0] = OSCL_NEW(ProgressiveDownloadState_HEAD, ());
    133             iState[1] = OSCL_NEW(ProgressiveDownloadState_GET, ());
    134             iInitStateNum = 0;
    135             iCurrStateNum = iInitStateNum;
    136             iCurrState = iState[iCurrStateNum];
    137 
    138             // create iComposer and iParser
    139             iComposer = HTTPComposer::create();
    140             iParser   = HttpParsingBasicObject::create();
    141         }
    142 
    143         // destructor
    144         virtual ~ProgressiveDownload()
    145         {
    146             uint32 i = 0;
    147             for (i = 0; i < NUM_PROGRESSIVE_DOWNLOAD_STATE; i++)
    148             {
    149                 if (iState[i]) OSCL_DELETE(iState[i]);
    150                 iState[i] = NULL;
    151             }
    152 
    153             OSCL_DELETE(iComposer);
    154             OSCL_DELETE(iParser);
    155         }
    156 
    157         void setConfigInfo(OsclAny* aConfigInfo)
    158         {
    159             iCfgFile = *((OsclSharedPtr<PVDlCfgFile> *)aConfigInfo);
    160             HttpBasedProtocol::setConfigInfo(aConfigInfo);
    161         }
    162 
    163 
    164         void initialize()
    165         {
    166             // pass iComposer and iParser down to each state
    167             uint32 i = 0;
    168             for (i = 0; i < NUM_PROGRESSIVE_DOWNLOAD_STATE; i++)
    169             {
    170                 iState[i]->setObserver(this);
    171                 iState[i]->setComposer(iComposer);
    172                 iState[i]->setParser(iParser);
    173             }
    174             if (iCfgFile.GetRep())
    175             {
    176                 if (iCfgFile->getHttpHeadRequestDisabled())
    177                 {
    178                     iInitStateNum = 1;
    179                     iCurrStateNum = iInitStateNum;
    180                     iCurrState = iState[iCurrStateNum];
    181                 }
    182             }
    183         }
    184 
    185         void reset()
    186         {
    187             HttpBasedProtocol::reset();
    188             iCurrStateNum = 0;
    189             iCurrState = iState[iCurrStateNum];
    190         }
    191 
    192     protected:
    193         // state transition
    194         ProtocolState* getNextState()
    195         {
    196             // release the memory for the current state
    197             if (++iCurrStateNum >= NUM_PROGRESSIVE_DOWNLOAD_STATE) iCurrStateNum = iInitStateNum;
    198             return iState[iCurrStateNum];
    199         }
    200 
    201     protected:
    202         DownloadState *iState[NUM_PROGRESSIVE_DOWNLOAD_STATE];
    203         uint32 iCurrStateNum;
    204         OsclSharedPtr<PVDlCfgFile> iCfgFile;
    205         uint32 iInitStateNum;
    206 };
    207 
    208 class ProgressiveStreaming : public ProgressiveDownload
    209 {
    210     public:
    211         ProgressiveStreaming(): ProgressiveDownload()
    212         {
    213 
    214             OSCL_DELETE(iState[DEFAULT_STATE_NUMBER_FOR_DOWNLOAD_GET_REQUEST]);
    215             iState[DEFAULT_STATE_NUMBER_FOR_DOWNLOAD_GET_REQUEST] = OSCL_NEW(ProgressiveStreamingState_GET, ());
    216             if (iParser) iParser->setNumRetry(MAX_NUM_EOS_MESSAGES_FOR_SAME_REQUEST + 1); // +1 for testing purpose (i.e., insert an EOS)
    217         }
    218 
    219         virtual void seek(const uint32 aSeekPosition)
    220         {
    221             HttpBasedProtocol::seek(aSeekPosition);
    222 
    223             // reset EOS related variables inside the parser
    224             if (iParser) iParser->resetForBadConnectionDetection();
    225         }
    226 };
    227 
    228 #endif // PVMF_PROTOCOLENGINE_PROGRESSIVE_DOWNLOAD_H_INCLUDED
    229 
    230