2009-10-09 Chris Toshok <toshok@ximian.com>
[moon.git] / src / mms-downloader.h
blob9c0b3b9b76729cbc3586bfafcc25fafecd4636cf
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: t; c-basic-offset: 8 -*- */
2 /*
3 * mms-downloader.h: MMS Downloader class.
5 * Contact:
6 * Moonlight List (moonlist-list@lists.ximian.com)
8 * Copyright 2008 Novell, Inc. (http://www.novell.com)
10 * See the LICENSE file included with the distribution for details.
14 #ifndef __MMS_DOWNLOADER_H__
15 #define __MMS_DOWNLOADER_H__
17 #include <glib.h>
19 class MmsDownloader;
20 class ContentDescriptionList;
22 #include "internal-downloader.h"
23 #include "downloader.h"
24 #include "http-streaming.h"
25 #include "pipeline.h"
26 #include "pipeline-asf.h"
27 #include "mutex.h"
29 #define MMS_DATA 0x44
30 #define MMS_HEADER 0x48
31 #define MMS_METADATA 0x4D
32 #define MMS_STREAM_C 0x43
33 #define MMS_END 0x45
34 #define MMS_PAIR_P 0x50
36 struct MmsHeader {
37 char b:1;
38 char frame:7;
39 guint8 id;
40 guint16 length;
43 struct MmsHeaderReason {
44 char b:1;
45 char frame:7;
46 guint8 id;
47 guint16 length;
48 guint32 reason;
51 struct MmsDataPacket {
52 guint32 id;
53 guint8 incarnation;
54 guint8 flags;
55 guint16 size;
58 struct MmsPacket {
59 union {
60 guint32 reason;
61 MmsDataPacket data;
62 } packet;
65 typedef struct MmsHeader MmsHeader;
66 typedef struct MmsPacket MmsPacket;
68 class MmsDownloader : public InternalDownloader {
69 private:
70 char *uri;
71 char *buffer;
72 char *client_id;
73 char *playlist_gen_id;
74 bool failure_reported;
76 guint32 size;
78 guint64 requested_pts;
79 Mutex request_mutex;
81 TimeSpan p_packet_times[3];
82 gint32 p_packet_sizes[3];
83 guint8 p_packet_count;
84 guint64 max_bitrate;
86 bool is_playing;
87 bool stream_switched;
89 MmsSource *source;
90 ContentDescriptionList *content_descriptions;
92 static void PlayCallback (EventObject *sender);
93 void Play (); // sends a play request. if SetRequestedPts has been called, start from that pts
94 void SelectStreams (); // sends a select stream request
96 bool ProcessPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
98 bool ProcessDataPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
99 bool ProcessHeaderPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
100 bool ProcessMetadataPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
101 bool ProcessPairPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
102 bool ProcessStreamSwitchPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
103 bool ProcessEndPacket (MmsHeader *header, MmsPacket *packet, char *payload, guint32 *size);
105 static void ProcessResponseHeaderCallback (gpointer context, const char *header, const char *value);
106 void ProcessResponseHeader (const char *header, const char *value);
108 protected:
109 virtual ~MmsDownloader ();
111 public:
112 MmsDownloader (Downloader *dl);
114 virtual void Open (const char *verb, const char *uri);
115 virtual void Write (void *buf, gint32 offset, gint32 n);
116 virtual char *GetDownloadedFilename (const char *partname);
117 virtual char *GetResponseText (const char *partname, gint64 *size);
118 virtual void SetFilename (const char *fname) { /* we don't need this */ }
120 void SetSource (MmsSource *src); // main thread only
121 MmsPlaylistEntry *GetCurrentEntryReffed (); // main thread only
123 void SetRequestedPts (guint64 value); // thread safe
124 guint64 GetRequestedPts (); // thread safe
126 const char *GetUri () { return uri; }
127 const char *GetClientId () { return client_id; }
128 const char *GetPlaylistGenId () { return playlist_gen_id; }
129 guint64 GetMaxBitrate () { return max_bitrate; }
132 class ContentDescriptionList {
133 public:
134 List list;
135 bool Parse (const char *input, gint32 length);
138 class ContentDescription : public List::Node {
139 public:
140 enum ValueType {
141 VT_BOOL = 11,
142 VT_BSTR = 8,
143 VT_CY = 6,
144 VT_ERROR = 10,
145 VT_I1 = 16,
146 VT_I2 = 2,
147 VT_I4 = 3,
148 VT_INT = 22,
149 VT_LPWSTR = 31,
150 VT_UI1 = 17,
151 VT_UI2 = 18,
152 VT_UI4 = 19,
153 VT_UINT = 23,
156 public:
157 virtual ~ContentDescription ();
158 char *name;
159 ValueType value_type;
160 void *value;
161 int value_length;
164 class MmsSecondDownloader : public EventObject {
165 private:
166 Downloader *dl;
167 MmsDownloader *mms;
168 guint kill_timeout;
170 EVENTHANDLER (MmsSecondDownloader, DownloadFailed, EventObject, EventArgs);
171 EVENTHANDLER (MmsSecondDownloader, Completed, EventObject, EventArgs);
172 static void data_write (void *data, gint32 offset, gint32 n, void *closure);
173 void CreateDownloader ();
174 static gboolean KillTimeoutCallback (gpointer context);
175 void KillTimeoutHandler ();
177 protected:
178 virtual ~MmsSecondDownloader () {}
180 public:
181 MmsSecondDownloader (MmsDownloader *mms);
183 virtual void Dispose ();
184 void SendStreamSwitch ();
185 // TODO: void SendLog ();
186 void SetKillTimeout (guint seconds); // the second downloader will kill itself after this amount of time
189 #endif /* __MMS_DOWNLOADER_H__ */