|
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
|
2 /* This Source Code Form is subject to the terms of the Mozilla Public |
|
3 * License, v. 2.0. If a copy of the MPL was not distributed with this |
|
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ |
|
5 |
|
6 #ifndef nsUnknownDecoder_h__ |
|
7 #define nsUnknownDecoder_h__ |
|
8 |
|
9 #include "nsIStreamConverter.h" |
|
10 #include "nsIContentSniffer.h" |
|
11 |
|
12 #include "nsCOMPtr.h" |
|
13 #include "nsString.h" |
|
14 |
|
15 #define NS_UNKNOWNDECODER_CID \ |
|
16 { /* 7d7008a0-c49a-11d3-9b22-0080c7cb1080 */ \ |
|
17 0x7d7008a0, \ |
|
18 0xc49a, \ |
|
19 0x11d3, \ |
|
20 {0x9b, 0x22, 0x00, 0x80, 0xc7, 0xcb, 0x10, 0x80} \ |
|
21 } |
|
22 |
|
23 |
|
24 class nsUnknownDecoder : public nsIStreamConverter, public nsIContentSniffer |
|
25 { |
|
26 public: |
|
27 // nsISupports methods |
|
28 NS_DECL_ISUPPORTS |
|
29 |
|
30 // nsIStreamConverter methods |
|
31 NS_DECL_NSISTREAMCONVERTER |
|
32 |
|
33 // nsIStreamListener methods |
|
34 NS_DECL_NSISTREAMLISTENER |
|
35 |
|
36 // nsIRequestObserver methods |
|
37 NS_DECL_NSIREQUESTOBSERVER |
|
38 |
|
39 // nsIContentSniffer methods |
|
40 NS_DECL_NSICONTENTSNIFFER |
|
41 |
|
42 nsUnknownDecoder(); |
|
43 |
|
44 protected: |
|
45 virtual ~nsUnknownDecoder(); |
|
46 |
|
47 virtual void DetermineContentType(nsIRequest* aRequest); |
|
48 nsresult FireListenerNotifications(nsIRequest* request, nsISupports *aCtxt); |
|
49 |
|
50 protected: |
|
51 nsCOMPtr<nsIStreamListener> mNextListener; |
|
52 |
|
53 // Function to use to check whether sniffing some potentially |
|
54 // dangerous types (eg HTML) is ok for this request. We can disable |
|
55 // sniffing for local files if needed using this. Just a security |
|
56 // precation thingy... who knows when we suddenly need to flip this |
|
57 // pref? |
|
58 bool AllowSniffing(nsIRequest* aRequest); |
|
59 |
|
60 // Various sniffer functions. Returning true means that a type |
|
61 // was determined; false means no luck. |
|
62 bool SniffForHTML(nsIRequest* aRequest); |
|
63 bool SniffForXML(nsIRequest* aRequest); |
|
64 |
|
65 // SniffURI guesses at the content type based on the URI (typically |
|
66 // using the extentsion) |
|
67 bool SniffURI(nsIRequest* aRequest); |
|
68 |
|
69 // LastDitchSniff guesses at text/plain vs. application/octet-stream |
|
70 // by just looking at whether the data contains null bytes, and |
|
71 // maybe at the fraction of chars with high bit set. Use this only |
|
72 // as a last-ditch attempt to decide a content type! |
|
73 bool LastDitchSniff(nsIRequest* aRequest); |
|
74 |
|
75 /** |
|
76 * An entry struct for our array of sniffers. Each entry has either |
|
77 * a type associated with it (set these with the SNIFFER_ENTRY macro) |
|
78 * or a function to be executed (set these with the |
|
79 * SNIFFER_ENTRY_WITH_FUNC macro). The function should take a single |
|
80 * nsIRequest* and returns bool -- true if it sets mContentType, |
|
81 * false otherwise |
|
82 */ |
|
83 struct nsSnifferEntry { |
|
84 typedef bool (nsUnknownDecoder::*TypeSniffFunc)(nsIRequest* aRequest); |
|
85 |
|
86 const char* mBytes; |
|
87 uint32_t mByteLen; |
|
88 |
|
89 // Exactly one of mMimeType and mContentTypeSniffer should be set non-null |
|
90 const char* mMimeType; |
|
91 TypeSniffFunc mContentTypeSniffer; |
|
92 }; |
|
93 |
|
94 #define SNIFFER_ENTRY(_bytes, _type) \ |
|
95 { _bytes, sizeof(_bytes) - 1, _type, nullptr } |
|
96 |
|
97 #define SNIFFER_ENTRY_WITH_FUNC(_bytes, _func) \ |
|
98 { _bytes, sizeof(_bytes) - 1, nullptr, _func } |
|
99 |
|
100 static nsSnifferEntry sSnifferEntries[]; |
|
101 static uint32_t sSnifferEntryNum; |
|
102 |
|
103 char *mBuffer; |
|
104 uint32_t mBufferLen; |
|
105 bool mRequireHTMLsuffix; |
|
106 |
|
107 nsCString mContentType; |
|
108 |
|
109 }; |
|
110 |
|
111 #define NS_BINARYDETECTOR_CID \ |
|
112 { /* a2027ec6-ba0d-4c72-805d-148233f5f33c */ \ |
|
113 0xa2027ec6, \ |
|
114 0xba0d, \ |
|
115 0x4c72, \ |
|
116 {0x80, 0x5d, 0x14, 0x82, 0x33, 0xf5, 0xf3, 0x3c} \ |
|
117 } |
|
118 |
|
119 /** |
|
120 * Class that detects whether a data stream is text or binary. This reuses |
|
121 * most of nsUnknownDecoder except the actual content-type determination logic |
|
122 * -- our overridden DetermineContentType simply calls LastDitchSniff and sets |
|
123 * the type to APPLICATION_GUESS_FROM_EXT if the data is detected as binary. |
|
124 */ |
|
125 class nsBinaryDetector : public nsUnknownDecoder |
|
126 { |
|
127 protected: |
|
128 virtual void DetermineContentType(nsIRequest* aRequest); |
|
129 }; |
|
130 |
|
131 #define NS_BINARYDETECTOR_CATEGORYENTRY \ |
|
132 { NS_CONTENT_SNIFFER_CATEGORY, "Binary Detector", NS_BINARYDETECTOR_CONTRACTID } |
|
133 |
|
134 #endif /* nsUnknownDecoder_h__ */ |
|
135 |