| Differences between
and this patch
- a/WebCore/Android.mk +1 lines
Lines 892-897 LOCAL_SRC_FILES := $(LOCAL_SRC_FILES) \ a/WebCore/Android.mk_sec1
892
	workers/WorkerScriptLoader.cpp \
892
	workers/WorkerScriptLoader.cpp \
893
	workers/WorkerThread.cpp \
893
	workers/WorkerThread.cpp \
894
	\
894
	\
895
	xml/DOMFormData.cpp \
895
	xml/DOMParser.cpp \
896
	xml/DOMParser.cpp \
896
	xml/XMLHttpRequest.cpp \
897
	xml/XMLHttpRequest.cpp \
897
	xml/XMLHttpRequestUpload.cpp \
898
	xml/XMLHttpRequestUpload.cpp \
- a/WebCore/ChangeLog +40 lines
Lines 1-3 a/WebCore/ChangeLog_sec1
1
2010-03-03  Jian Li  <jianli@chromium.org>
2
3
        Reviewed by NOBODY (OOPS!).
4
5
        Implementing DOMFormData class.
6
        https://bugs.webkit.org/show_bug.cgi?id=35707
7
8
        This patch only addresses the implementation of DOMFormData class and
9
        moves the FormData construction logic from HTMLFormElement::createFormData
10
        to FormData::create() so that it can be used by both HTMLFormElement
11
        and XMLHttpRequest.
12
13
        The DOMFormData IDL interface will be exposed in another patch and the
14
        test will be added then.
15
16
        * Android.mk:
17
        * GNUmakefile.am:
18
        * WebCore.gypi:
19
        * WebCore.pro:
20
        * WebCore.vcproj/WebCore.vcproj:
21
        * WebCore.xcodeproj/project.pbxproj:
22
        * html/FormDataList.cpp:
23
        (WebCore::FormDataList::FormDataList):
24
        * html/FormDataList.h:
25
        (WebCore::FormDataList::encoding):
26
        * html/HTMLFormElement.cpp:
27
        (WebCore::HTMLFormElement::createFormData):
28
        (WebCore::HTMLFormElement::submit):
29
        (WebCore::HTMLFormElement::createDOMFormData):
30
        * html/HTMLFormElement.h:
31
        * platform/network/FormData.cpp:
32
        (WebCore::FormData::create):
33
        * platform/network/FormData.h:
34
        (WebCore::FormData::boundary):
35
        * xml/DOMFormData.cpp: Added.
36
        * xml/DOMFormData.h: Added.
37
        * xml/XMLHttpRequest.cpp:
38
        (WebCore::XMLHttpRequest::send):
39
        * xml/XMLHttpRequest.h:
40
1
2010-03-03  Darin Adler  <darin@apple.com>
41
2010-03-03  Darin Adler  <darin@apple.com>
2
42
3
        Fixed Mac build.
43
        Fixed Mac build.
- a/WebCore/GNUmakefile.am +2 lines
Lines 1953-1958 webcore_sources += \ a/WebCore/GNUmakefile.am_sec1
1953
	WebCore/rendering/style/StyleTransformData.h \
1953
	WebCore/rendering/style/StyleTransformData.h \
1954
	WebCore/rendering/style/StyleVisualData.cpp \
1954
	WebCore/rendering/style/StyleVisualData.cpp \
1955
	WebCore/rendering/style/StyleVisualData.h \
1955
	WebCore/rendering/style/StyleVisualData.h \
1956
	WebCore/xml/DOMFormData.cpp \
1957
	WebCore/xml/DOMFormData.h \
1956
	WebCore/xml/DOMParser.cpp \
1958
	WebCore/xml/DOMParser.cpp \
1957
	WebCore/xml/DOMParser.h \
1959
	WebCore/xml/DOMParser.h \
1958
	WebCore/xml/XMLHttpRequest.cpp \
1960
	WebCore/xml/XMLHttpRequest.cpp \
- a/WebCore/WebCore.gypi +2 lines
Lines 3661-3666 a/WebCore/WebCore.gypi_sec1
3661
            'workers/WorkerScriptLoaderClient.h',
3661
            'workers/WorkerScriptLoaderClient.h',
3662
            'workers/WorkerThread.cpp',
3662
            'workers/WorkerThread.cpp',
3663
            'workers/WorkerThread.h',
3663
            'workers/WorkerThread.h',
3664
            'xml/DOMFormData.cpp',
3665
            'xml/DOMFormData.h',
3664
            'xml/DOMParser.cpp',
3666
            'xml/DOMParser.cpp',
3665
            'xml/DOMParser.h',
3667
            'xml/DOMParser.h',
3666
            'xml/NativeXPathNSResolver.cpp',
3668
            'xml/NativeXPathNSResolver.cpp',
- a/WebCore/WebCore.pro +2 lines
Lines 975-980 SOURCES += \ a/WebCore/WebCore.pro_sec1
975
    rendering/style/StyleSurroundData.cpp \
975
    rendering/style/StyleSurroundData.cpp \
976
    rendering/style/StyleTransformData.cpp \
976
    rendering/style/StyleTransformData.cpp \
977
    rendering/style/StyleVisualData.cpp \
977
    rendering/style/StyleVisualData.cpp \
978
    xml/DOMFormData.cpp \
978
    xml/DOMParser.cpp \
979
    xml/DOMParser.cpp \
979
    xml/XMLHttpRequest.cpp \
980
    xml/XMLHttpRequest.cpp \
980
    xml/XMLHttpRequestUpload.cpp \
981
    xml/XMLHttpRequestUpload.cpp \
Lines 1951-1956 HEADERS += \ a/WebCore/WebCore.pro_sec2
1951
    workers/WorkerRunLoop.h \
1952
    workers/WorkerRunLoop.h \
1952
    workers/WorkerScriptLoader.h \
1953
    workers/WorkerScriptLoader.h \
1953
    workers/WorkerThread.h \
1954
    workers/WorkerThread.h \
1955
    xml/DOMFormData.h \
1954
    xml/DOMParser.h \
1956
    xml/DOMParser.h \
1955
    xml/NativeXPathNSResolver.h \
1957
    xml/NativeXPathNSResolver.h \
1956
    xml/XMLHttpRequest.h \
1958
    xml/XMLHttpRequest.h \
- a/WebCore/WebCore.vcproj/WebCore.vcproj +8 lines
Lines 28267-28272 a/WebCore/WebCore.vcproj/WebCore.vcproj_sec1
28267
			Name="xml"
28267
			Name="xml"
28268
			>
28268
			>
28269
			<File
28269
			<File
28270
				RelativePath="..\xml\DOMFormData.cpp"
28271
				>
28272
			</File>
28273
			<File
28274
				RelativePath="..\xml\DOMFormData.h"
28275
				>
28276
			</File>
28277
			<File
28270
				RelativePath="..\xml\DOMParser.cpp"
28278
				RelativePath="..\xml\DOMParser.cpp"
28271
				>
28279
				>
28272
			</File>
28280
			</File>
- a/WebCore/WebCore.xcodeproj/project.pbxproj +8 lines
Lines 625-630 a/WebCore/WebCore.xcodeproj/project.pbxproj_sec1
625
		2ECF7ADD10162B3800427DE7 /* JSErrorEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = 2ECF7ADB10162B3800427DE7 /* JSErrorEvent.h */; };
625
		2ECF7ADD10162B3800427DE7 /* JSErrorEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = 2ECF7ADB10162B3800427DE7 /* JSErrorEvent.h */; };
626
		2ECF7AE110162B5800427DE7 /* ErrorEvent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2ECF7ADE10162B5800427DE7 /* ErrorEvent.cpp */; };
626
		2ECF7AE110162B5800427DE7 /* ErrorEvent.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2ECF7ADE10162B5800427DE7 /* ErrorEvent.cpp */; };
627
		2ECF7AE210162B5800427DE7 /* ErrorEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = 2ECF7ADF10162B5800427DE7 /* ErrorEvent.h */; };
627
		2ECF7AE210162B5800427DE7 /* ErrorEvent.h in Headers */ = {isa = PBXBuildFile; fileRef = 2ECF7ADF10162B5800427DE7 /* ErrorEvent.h */; };
628
		2ED60955113F284900C8684E /* DOMFormData.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 2ED60953113F284900C8684E /* DOMFormData.cpp */; };
629
		2ED60956113F284900C8684E /* DOMFormData.h in Headers */ = {isa = PBXBuildFile; fileRef = 2ED60954113F284900C8684E /* DOMFormData.h */; };
628
		31288E720E3005D6003619AE /* WebKitCSSKeyframeRule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 31288E6E0E3005D6003619AE /* WebKitCSSKeyframeRule.cpp */; };
630
		31288E720E3005D6003619AE /* WebKitCSSKeyframeRule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 31288E6E0E3005D6003619AE /* WebKitCSSKeyframeRule.cpp */; };
629
		31288E730E3005D6003619AE /* WebKitCSSKeyframeRule.h in Headers */ = {isa = PBXBuildFile; fileRef = 31288E6F0E3005D6003619AE /* WebKitCSSKeyframeRule.h */; };
631
		31288E730E3005D6003619AE /* WebKitCSSKeyframeRule.h in Headers */ = {isa = PBXBuildFile; fileRef = 31288E6F0E3005D6003619AE /* WebKitCSSKeyframeRule.h */; };
630
		31288E740E3005D6003619AE /* WebKitCSSKeyframesRule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 31288E700E3005D6003619AE /* WebKitCSSKeyframesRule.cpp */; };
632
		31288E740E3005D6003619AE /* WebKitCSSKeyframesRule.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 31288E700E3005D6003619AE /* WebKitCSSKeyframesRule.cpp */; };
Lines 5970-5975 a/WebCore/WebCore.xcodeproj/project.pbxproj_sec2
5970
		2ECF7ADE10162B5800427DE7 /* ErrorEvent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ErrorEvent.cpp; sourceTree = "<group>"; };
5972
		2ECF7ADE10162B5800427DE7 /* ErrorEvent.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ErrorEvent.cpp; sourceTree = "<group>"; };
5971
		2ECF7ADF10162B5800427DE7 /* ErrorEvent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ErrorEvent.h; sourceTree = "<group>"; };
5973
		2ECF7ADF10162B5800427DE7 /* ErrorEvent.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ErrorEvent.h; sourceTree = "<group>"; };
5972
		2ECF7AE010162B5800427DE7 /* ErrorEvent.idl */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = ErrorEvent.idl; sourceTree = "<group>"; };
5974
		2ECF7AE010162B5800427DE7 /* ErrorEvent.idl */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = ErrorEvent.idl; sourceTree = "<group>"; };
5975
		2ED60953113F284900C8684E /* DOMFormData.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = DOMFormData.cpp; sourceTree = "<group>"; };
5976
		2ED60954113F284900C8684E /* DOMFormData.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = DOMFormData.h; sourceTree = "<group>"; };
5973
		31288E6E0E3005D6003619AE /* WebKitCSSKeyframeRule.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WebKitCSSKeyframeRule.cpp; sourceTree = "<group>"; };
5977
		31288E6E0E3005D6003619AE /* WebKitCSSKeyframeRule.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WebKitCSSKeyframeRule.cpp; sourceTree = "<group>"; };
5974
		31288E6F0E3005D6003619AE /* WebKitCSSKeyframeRule.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WebKitCSSKeyframeRule.h; sourceTree = "<group>"; };
5978
		31288E6F0E3005D6003619AE /* WebKitCSSKeyframeRule.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WebKitCSSKeyframeRule.h; sourceTree = "<group>"; };
5975
		31288E700E3005D6003619AE /* WebKitCSSKeyframesRule.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WebKitCSSKeyframesRule.cpp; sourceTree = "<group>"; };
5979
		31288E700E3005D6003619AE /* WebKitCSSKeyframesRule.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WebKitCSSKeyframesRule.cpp; sourceTree = "<group>"; };
Lines 15332-15337 a/WebCore/WebCore.xcodeproj/project.pbxproj_sec3
15332
		E1F0424309839389006694EA /* xml */ = {
15336
		E1F0424309839389006694EA /* xml */ = {
15333
			isa = PBXGroup;
15337
			isa = PBXGroup;
15334
			children = (
15338
			children = (
15339
				2ED60953113F284900C8684E /* DOMFormData.cpp */,
15340
				2ED60954113F284900C8684E /* DOMFormData.h */,
15335
				1ACE53E10A8D18E70022947D /* DOMParser.cpp */,
15341
				1ACE53E10A8D18E70022947D /* DOMParser.cpp */,
15336
				1ACE53E20A8D18E70022947D /* DOMParser.h */,
15342
				1ACE53E20A8D18E70022947D /* DOMParser.h */,
15337
				1ACE53E30A8D18E70022947D /* DOMParser.idl */,
15343
				1ACE53E30A8D18E70022947D /* DOMParser.idl */,
Lines 18609-18614 a/WebCore/WebCore.xcodeproj/project.pbxproj_sec4
18609
				CE172E011136E8CE0062A533 /* ZoomMode.h in Headers */,
18615
				CE172E011136E8CE0062A533 /* ZoomMode.h in Headers */,
18610
				B5D3601A112F8B560048DEA8 /* DatabaseCallback.h in Headers */,
18616
				B5D3601A112F8B560048DEA8 /* DatabaseCallback.h in Headers */,
18611
				B5D3601D112F8BA00048DEA8 /* JSDatabaseCallback.h in Headers */,
18617
				B5D3601D112F8BA00048DEA8 /* JSDatabaseCallback.h in Headers */,
18618
				2ED60956113F284900C8684E /* DOMFormData.h in Headers */,
18612
			);
18619
			);
18613
			runOnlyForDeploymentPostprocessing = 0;
18620
			runOnlyForDeploymentPostprocessing = 0;
18614
		};
18621
		};
Lines 20799-20804 a/WebCore/WebCore.xcodeproj/project.pbxproj_sec5
20799
				596229781133EFD700DC4CBB /* GeolocationPositionCache.cpp in Sources */,
20806
				596229781133EFD700DC4CBB /* GeolocationPositionCache.cpp in Sources */,
20800
				0BC2C7771134A8FC000B2F61 /* CanvasSurface.cpp in Sources */,
20807
				0BC2C7771134A8FC000B2F61 /* CanvasSurface.cpp in Sources */,
20801
				B5D3601F112F8BA80048DEA8 /* JSDatabaseCallback.cpp in Sources */,
20808
				B5D3601F112F8BA80048DEA8 /* JSDatabaseCallback.cpp in Sources */,
20809
				2ED60955113F284900C8684E /* DOMFormData.cpp in Sources */,
20802
			);
20810
			);
20803
			runOnlyForDeploymentPostprocessing = 0;
20811
			runOnlyForDeploymentPostprocessing = 0;
20804
		};
20812
		};
- a/WebCore/html/FormDataList.cpp +7 lines
Lines 28-33 FormDataList::FormDataList(const TextEncoding& c) a/WebCore/html/FormDataList.cpp_sec1
28
{
28
{
29
}
29
}
30
30
31
FormDataList::FormDataList(const FormDataList& list)
32
    : m_encoding(list.encoding())
33
{
34
    for (unsigned i = 0; i < list.m_list.size(); i++)
35
        m_list.append(list.m_list[i]);
36
}
37
31
void FormDataList::appendString(const CString& s)
38
void FormDataList::appendString(const CString& s)
32
{
39
{
33
    m_list.append(s);
40
    m_list.append(s);
- a/WebCore/html/FormDataList.h +2 lines
Lines 30-35 namespace WebCore { a/WebCore/html/FormDataList.h_sec1
30
class FormDataList {
30
class FormDataList {
31
public:
31
public:
32
    FormDataList(const TextEncoding&);
32
    FormDataList(const TextEncoding&);
33
    FormDataList(const FormDataList&);
33
34
34
    void appendData(const String& key, const String& value)
35
    void appendData(const String& key, const String& value)
35
        { appendString(key); appendString(value); }
36
        { appendString(key); appendString(value); }
Lines 55-60 public: a/WebCore/html/FormDataList.h_sec2
55
    };
56
    };
56
57
57
    const Vector<Item>& list() const { return m_list; }
58
    const Vector<Item>& list() const { return m_list; }
59
    const TextEncoding& encoding() const { return m_encoding; }
58
60
59
private:
61
private:
60
    void appendString(const CString&);
62
    void appendString(const CString&);
- a/WebCore/html/HTMLFormElement.cpp -84 / +19 lines
Lines 26-33 a/WebCore/html/HTMLFormElement.cpp_sec1
26
#include "HTMLFormElement.h"
26
#include "HTMLFormElement.h"
27
27
28
#include "CSSHelper.h"
28
#include "CSSHelper.h"
29
#include "Chrome.h"
29
#include "DOMFormData.h"
30
#include "ChromeClient.h"
31
#include "Document.h"
30
#include "Document.h"
32
#include "Event.h"
31
#include "Event.h"
33
#include "EventNames.h"
32
#include "EventNames.h"
Lines 46-52 a/WebCore/html/HTMLFormElement.cpp_sec2
46
#include "ScriptEventListener.h"
45
#include "ScriptEventListener.h"
47
#include "MIMETypeRegistry.h"
46
#include "MIMETypeRegistry.h"
48
#include "MappedAttribute.h"
47
#include "MappedAttribute.h"
49
#include "Page.h"
50
#include "RenderTextControl.h"
48
#include "RenderTextControl.h"
51
#include "ValidityState.h"
49
#include "ValidityState.h"
52
#include <limits>
50
#include <limits>
Lines 201-283 TextEncoding HTMLFormElement::dataEncoding() const a/WebCore/html/HTMLFormElement.cpp_sec3
201
    return m_formDataBuilder.dataEncoding(document());
199
    return m_formDataBuilder.dataEncoding(document());
202
}
200
}
203
201
204
PassRefPtr<FormData> HTMLFormElement::createFormData(const CString& boundary)
202
PassRefPtr<FormData> HTMLFormElement::createFormData()
205
{
203
{
206
    Vector<char> encodedData;
204
    RefPtr<DOMFormData> domFormData = createDOMFormData();
207
    TextEncoding encoding = dataEncoding().encodingForFormSubmission();
208
205
209
    RefPtr<FormData> result = FormData::create();
206
    RefPtr<FormData> result = FormData::create(*domFormData, m_formDataBuilder.isMultiPartForm(), document());
210
211
    for (unsigned i = 0; i < formElements.size(); ++i) {
212
        HTMLFormControlElement* control = formElements[i];
213
        FormDataList list(encoding);
214
215
        if (!control->disabled() && control->appendFormData(list, m_formDataBuilder.isMultiPartForm())) {
216
            size_t formDataListSize = list.list().size();
217
            ASSERT(formDataListSize % 2 == 0);
218
            for (size_t j = 0; j < formDataListSize; j += 2) {
219
                const FormDataList::Item& key = list.list()[j];
220
                const FormDataList::Item& value = list.list()[j + 1];
221
                if (!m_formDataBuilder.isMultiPartForm()) {
222
                    // Omit the name "isindex" if it's the first form data element.
223
                    // FIXME: Why is this a good rule? Is this obsolete now?
224
                    if (encodedData.isEmpty() && key.data() == "isindex")
225
                        FormDataBuilder::encodeStringAsFormData(encodedData, value.data());
226
                    else
227
                        m_formDataBuilder.addKeyValuePairAsFormData(encodedData, key.data(), value.data());
228
                } else {
229
                    Vector<char> header;
230
                    m_formDataBuilder.beginMultiPartHeader(header, boundary, key.data());
231
232
                    bool shouldGenerateFile = false;
233
                    // if the current type is FILE, then we also need to include the filename
234
                    if (value.file()) {
235
                        const String& path = value.file()->path();
236
                        String fileName = value.file()->fileName();
237
238
                        // Let the application specify a filename if it's going to generate a replacement file for the upload.
239
                        if (!path.isEmpty()) {
240
                            if (Page* page = document()->page()) {
241
                                String generatedFileName;
242
                                shouldGenerateFile = page->chrome()->client()->shouldReplaceWithGeneratedFileForUpload(path, generatedFileName);
243
                                if (shouldGenerateFile)
244
                                    fileName = generatedFileName;
245
                            }
246
                        }
247
248
                        // We have to include the filename=".." part in the header, even if the filename is empty
249
                        m_formDataBuilder.addFilenameToMultiPartHeader(header, encoding, fileName);
250
251
                        if (!fileName.isEmpty()) {
252
                            // FIXME: The MIMETypeRegistry function's name makes it sound like it takes a path,
253
                            // not just a basename. But filename is not the path. But note that it's not safe to
254
                            // just use path instead since in the generated-file case it will not reflect the
255
                            // MIME type of the generated file.
256
                            String mimeType = MIMETypeRegistry::getMIMETypeForPath(fileName);
257
                            if (!mimeType.isEmpty())
258
                                m_formDataBuilder.addContentTypeToMultiPartHeader(header, mimeType.latin1());
259
                        }
260
                    }
261
262
                    m_formDataBuilder.finishMultiPartHeader(header);
263
264
                    // Append body
265
                    result->appendData(header.data(), header.size());
266
                    if (size_t dataSize = value.data().length())
267
                        result->appendData(value.data().data(), dataSize);
268
                    else if (value.file() && !value.file()->path().isEmpty())
269
                        result->appendFile(value.file()->path(), shouldGenerateFile);
270
271
                    result->appendData("\r\n", 2);
272
                }
273
            }
274
        }
275
    }
276
277
    if (m_formDataBuilder.isMultiPartForm())
278
        m_formDataBuilder.addBoundaryToMultiPartHeader(encodedData, boundary, true);
279
280
    result->appendData(encodedData.data(), encodedData.size());
281
207
282
    result->setIdentifier(generateFormDataIdentifier());
208
    result->setIdentifier(generateFormDataIdentifier());
283
    return result;
209
    return result;
Lines 389-396 void HTMLFormElement::submit(Event* event, bool activateSubmitButton, bool lockH a/WebCore/html/HTMLFormElement.cpp_sec4
389
            ASSERT(!m_formDataBuilder.isMultiPartForm());
315
            ASSERT(!m_formDataBuilder.isMultiPartForm());
390
        }
316
        }
391
317
318
        RefPtr<FormData> data = createFormData();
392
        if (!m_formDataBuilder.isMultiPartForm()) {
319
        if (!m_formDataBuilder.isMultiPartForm()) {
393
            RefPtr<FormData> data = createFormData(CString());
394
320
395
            if (isMailtoForm()) {
321
            if (isMailtoForm()) {
396
                // Convert the form data into a string that we put into the URL.
322
                // Convert the form data into a string that we put into the URL.
Lines 400-412 void HTMLFormElement::submit(Event* event, bool activateSubmitButton, bool lockH a/WebCore/html/HTMLFormElement.cpp_sec5
400
            }
326
            }
401
327
402
            frame->loader()->submitForm("POST", m_url, data.release(), m_target, m_formDataBuilder.encodingType(), String(), lockHistory, event, formState.release());
328
            frame->loader()->submitForm("POST", m_url, data.release(), m_target, m_formDataBuilder.encodingType(), String(), lockHistory, event, formState.release());
403
        } else {
329
        } else
404
            Vector<char> boundary = m_formDataBuilder.generateUniqueBoundaryString();
330
            frame->loader()->submitForm("POST", m_url, data.get(), m_target, m_formDataBuilder.encodingType(), data->boundary().data(), lockHistory, event, formState.release());
405
            frame->loader()->submitForm("POST", m_url, createFormData(boundary.data()), m_target, m_formDataBuilder.encodingType(), boundary.data(), lockHistory, event, formState.release());
406
        }
407
    } else {
331
    } else {
408
        m_formDataBuilder.setIsMultiPartForm(false);
332
        m_formDataBuilder.setIsMultiPartForm(false);
409
        frame->loader()->submitForm("GET", m_url, createFormData(CString()), m_target, String(), String(), lockHistory, event, formState.release());
333
        frame->loader()->submitForm("GET", m_url, createFormData(), m_target, String(), String(), lockHistory, event, formState.release());
410
    }
334
    }
411
335
412
    if (needButtonActivation && firstSuccessfulSubmitButton)
336
    if (needButtonActivation && firstSuccessfulSubmitButton)
Lines 685-688 void HTMLFormElement::didMoveToNewOwnerDocument() a/WebCore/html/HTMLFormElement.cpp_sec6
685
    HTMLElement::didMoveToNewOwnerDocument();
609
    HTMLElement::didMoveToNewOwnerDocument();
686
}
610
}
687
611
612
PassRefPtr<DOMFormData> HTMLFormElement::createDOMFormData()
613
{
614
    FormDataList list(dataEncoding().encodingForFormSubmission());
615
    for (unsigned i = 0; i < formElements.size(); ++i) {
616
        HTMLFormControlElement* control = formElements[i];
617
        if (!control->disabled())
618
            control->appendFormData(list, m_formDataBuilder.isMultiPartForm());
619
    }
620
    return DOMFormData::create(list);
621
}
622
688
} // namespace
623
} // namespace
- a/WebCore/html/HTMLFormElement.h -1 / +4 lines
Lines 32-37 a/WebCore/html/HTMLFormElement.h_sec1
32
32
33
namespace WebCore {
33
namespace WebCore {
34
34
35
class DOMFormData;
35
class Event;
36
class Event;
36
class FormData;
37
class FormData;
37
class HTMLFormControlElement;
38
class HTMLFormControlElement;
Lines 125-130 public: a/WebCore/html/HTMLFormElement.h_sec2
125
    CheckedRadioButtons& checkedRadioButtons() { return m_checkedRadioButtons; }
126
    CheckedRadioButtons& checkedRadioButtons() { return m_checkedRadioButtons; }
126
    
127
    
127
    virtual void documentDidBecomeActive();
128
    virtual void documentDidBecomeActive();
129
    
130
    PassRefPtr<DOMFormData> createDOMFormData();
128
131
129
protected:
132
protected:
130
    virtual void willMoveToNewOwnerDocument();
133
    virtual void willMoveToNewOwnerDocument();
Lines 135-141 private: a/WebCore/html/HTMLFormElement.h_sec3
135
138
136
    bool isMailtoForm() const;
139
    bool isMailtoForm() const;
137
    TextEncoding dataEncoding() const;
140
    TextEncoding dataEncoding() const;
138
    PassRefPtr<FormData> createFormData(const CString& boundary);
141
    PassRefPtr<FormData> createFormData();
139
    unsigned formElementIndex(HTMLFormControlElement*);
142
    unsigned formElementIndex(HTMLFormControlElement*);
140
143
141
    friend class HTMLFormCollection;
144
    friend class HTMLFormCollection;
- a/WebCore/platform/network/FormData.cpp +86 lines
Lines 22-29 a/WebCore/platform/network/FormData.cpp_sec1
22
#include "FormData.h"
22
#include "FormData.h"
23
23
24
#include "CString.h"
24
#include "CString.h"
25
#include "Chrome.h"
25
#include "ChromeClient.h"
26
#include "ChromeClient.h"
27
#include "DOMFormData.h"
28
#include "Document.h"
26
#include "FileSystem.h"
29
#include "FileSystem.h"
30
#include "FormDataBuilder.h"
31
#include "FormDataList.h"
32
#include "MIMETypeRegistry.h"
33
#include "Page.h"
27
#include "TextEncoding.h"
34
#include "TextEncoding.h"
28
35
29
namespace WebCore {
36
namespace WebCore {
Lines 88-93 PassRefPtr<FormData> FormData::create(const Vector<char>& vector) a/WebCore/platform/network/FormData.cpp_sec2
88
    return result.release();
95
    return result.release();
89
}
96
}
90
97
98
PassRefPtr<FormData> FormData::create(const DOMFormData& domFormData, bool isMultiPartForm, Document* document)
99
{
100
    RefPtr<FormData> result = create();
101
    
102
    FormDataBuilder formDataBuilder;
103
    if (isMultiPartForm)
104
        result->m_boundary = formDataBuilder.generateUniqueBoundaryString();
105
106
    Vector<char> encodedData;
107
    TextEncoding encoding = domFormData.list().encoding();
108
109
    const Vector<FormDataList::Item>& list = domFormData.list().list();
110
    size_t formDataListSize = list.size();
111
    ASSERT(!(formDataListSize % 2));
112
    for (size_t i = 0; i < formDataListSize; i += 2) {
113
        const FormDataList::Item& key = list[i];
114
        const FormDataList::Item& value = list[i + 1];
115
        if (isMultiPartForm) {
116
            Vector<char> header;
117
            formDataBuilder.beginMultiPartHeader(header, result->m_boundary.data(), key.data());
118
119
            bool shouldGenerateFile = false;
120
            // If the current type is FILE, then we also need to include the filename
121
            if (value.file()) {
122
                const String& path = value.file()->path();
123
                String fileName = value.file()->fileName();
124
125
                // Let the application specify a filename if it's going to generate a replacement file for the upload.
126
                if (!path.isEmpty()) {
127
                    if (Page* page = document->page()) {
128
                        String generatedFileName;
129
                        shouldGenerateFile = page->chrome()->client()->shouldReplaceWithGeneratedFileForUpload(path, generatedFileName);
130
                        if (shouldGenerateFile)
131
                            fileName = generatedFileName;
132
                    }
133
                }
134
135
                // We have to include the filename=".." part in the header, even if the filename is empty
136
                formDataBuilder.addFilenameToMultiPartHeader(header, encoding, fileName);
137
138
                if (!fileName.isEmpty()) {
139
                    // FIXME: The MIMETypeRegistry function's name makes it sound like it takes a path,
140
                    // not just a basename. But filename is not the path. But note that it's not safe to
141
                    // just use path instead since in the generated-file case it will not reflect the
142
                    // MIME type of the generated file.
143
                    String mimeType = MIMETypeRegistry::getMIMETypeForPath(fileName);
144
                    if (!mimeType.isEmpty())
145
                        formDataBuilder.addContentTypeToMultiPartHeader(header, mimeType.latin1());
146
                }
147
            }
148
149
            formDataBuilder.finishMultiPartHeader(header);
150
151
            // Append body
152
            result->appendData(header.data(), header.size());
153
            if (size_t dataSize = value.data().length())
154
                result->appendData(value.data().data(), dataSize);
155
            else if (value.file() && !value.file()->path().isEmpty())
156
                result->appendFile(value.file()->path(), shouldGenerateFile);
157
158
            result->appendData("\r\n", 2);
159
        } else {
160
            // Omit the name "isindex" if it's the first form data element.
161
            // FIXME: Why is this a good rule? Is this obsolete now?
162
            if (encodedData.isEmpty() && key.data() == "isindex")
163
                FormDataBuilder::encodeStringAsFormData(encodedData, value.data());
164
            else
165
                formDataBuilder.addKeyValuePairAsFormData(encodedData, key.data(), value.data());
166
        }
167
    } 
168
169
    if (isMultiPartForm)
170
        formDataBuilder.addBoundaryToMultiPartHeader(encodedData, result->m_boundary.data(), true);
171
172
    result->appendData(encodedData.data(), encodedData.size());
173
174
    return result.release();
175
}
176
91
PassRefPtr<FormData> FormData::copy() const
177
PassRefPtr<FormData> FormData::copy() const
92
{
178
{
93
    return adoptRef(new FormData(*this));
179
    return adoptRef(new FormData(*this));
- a/WebCore/platform/network/FormData.h +5 lines
Lines 27-32 a/WebCore/platform/network/FormData.h_sec1
27
namespace WebCore {
27
namespace WebCore {
28
28
29
class ChromeClient;
29
class ChromeClient;
30
class DOMFormData;
31
class Document;
30
32
31
class FormDataElement {
33
class FormDataElement {
32
public:
34
public:
Lines 67-72 public: a/WebCore/platform/network/FormData.h_sec2
67
    static PassRefPtr<FormData> create(const void*, size_t);
69
    static PassRefPtr<FormData> create(const void*, size_t);
68
    static PassRefPtr<FormData> create(const CString&);
70
    static PassRefPtr<FormData> create(const CString&);
69
    static PassRefPtr<FormData> create(const Vector<char>&);
71
    static PassRefPtr<FormData> create(const Vector<char>&);
72
    static PassRefPtr<FormData> create(const DOMFormData&, bool isMultiPartForm, Document*);
70
    PassRefPtr<FormData> copy() const;
73
    PassRefPtr<FormData> copy() const;
71
    PassRefPtr<FormData> deepCopy() const;
74
    PassRefPtr<FormData> deepCopy() const;
72
    ~FormData();
75
    ~FormData();
Lines 79-84 public: a/WebCore/platform/network/FormData.h_sec3
79
82
80
    bool isEmpty() const { return m_elements.isEmpty(); }
83
    bool isEmpty() const { return m_elements.isEmpty(); }
81
    const Vector<FormDataElement>& elements() const { return m_elements; }
84
    const Vector<FormDataElement>& elements() const { return m_elements; }
85
    const Vector<char>& boundary() const { return m_boundary; }
82
86
83
    void generateFiles(ChromeClient*);
87
    void generateFiles(ChromeClient*);
84
    void removeGeneratedFilesIfNeeded();
88
    void removeGeneratedFilesIfNeeded();
Lines 99-104 private: a/WebCore/platform/network/FormData.h_sec4
99
    int64_t m_identifier;
103
    int64_t m_identifier;
100
    bool m_hasGeneratedFiles;
104
    bool m_hasGeneratedFiles;
101
    bool m_alwaysStream;
105
    bool m_alwaysStream;
106
    Vector<char> m_boundary;
102
};
107
};
103
108
104
inline bool operator==(const FormData& a, const FormData& b)
109
inline bool operator==(const FormData& a, const FormData& b)
- a/WebCore/xml/DOMFormData.cpp +61 lines
Line 0 a/WebCore/xml/DOMFormData.cpp_sec1
1
/*
2
 * Copyright (C) 2010 Google Inc. All rights reserved.
3
 *
4
 * Redistribution and use in source and binary forms, with or without
5
 * modification, are permitted provided that the following conditions are
6
 * met:
7
 *
8
 *     * Redistributions of source code must retain the above copyright
9
 * notice, this list of conditions and the following disclaimer.
10
 *     * Redistributions in binary form must reproduce the above
11
 * copyright notice, this list of conditions and the following disclaimer
12
 * in the documentation and/or other materials provided with the
13
 * distribution.
14
 *     * Neither the name of Google Inc. nor the names of its
15
 * contributors may be used to endorse or promote products derived from
16
 * this software without specific prior written permission.
17
 *
18
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
 */
30
31
#include "config.h"
32
#include "DOMFormData.h"
33
34
#include "Blob.h"
35
#include "PlatformString.h"
36
37
namespace WebCore {
38
39
DOMFormData::DOMFormData() : m_list(UTF8Encoding())
40
{
41
}
42
43
DOMFormData::DOMFormData(const FormDataList& list) : m_list(list)
44
{
45
}
46
47
void DOMFormData::append(const String& name, const String& value)
48
{
49
    if (!name.isEmpty())
50
        m_list.appendData(name, value);
51
}
52
53
void DOMFormData::append(const String& name, Blob* blob)
54
{
55
    if (!name.isEmpty() && !blob->path().isEmpty()) {
56
        RefPtr<File> file = static_cast<File*>(blob);
57
        m_list.appendFile(name, file.release());
58
    }
59
}
60
61
} // namespace WebCore
- a/WebCore/xml/DOMFormData.h +69 lines
Line 0 a/WebCore/xml/DOMFormData.h_sec1
1
/*
2
 * Copyright (C) 2010 Google Inc. All rights reserved.
3
 *
4
 * Redistribution and use in source and binary forms, with or without
5
 * modification, are permitted provided that the following conditions are
6
 * met:
7
 *
8
 *     * Redistributions of source code must retain the above copyright
9
 * notice, this list of conditions and the following disclaimer.
10
 *     * Redistributions in binary form must reproduce the above
11
 * copyright notice, this list of conditions and the following disclaimer
12
 * in the documentation and/or other materials provided with the
13
 * distribution.
14
 *     * Neither the name of Google Inc. nor the names of its
15
 * contributors may be used to endorse or promote products derived from
16
 * this software without specific prior written permission.
17
 *
18
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
19
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
20
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
21
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
22
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
23
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
24
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
28
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
 */
30
31
#ifndef DOMFormData_h
32
#define DOMFormData_h
33
34
#include "FormDataList.h"
35
#include "TextEncoding.h"
36
#include <wtf/PassRefPtr.h>
37
#include <wtf/RefCounted.h>
38
39
namespace WebCore {
40
41
class Blob;
42
class String;
43
44
class DOMFormData : public RefCounted<DOMFormData> {
45
public:
46
    static PassRefPtr<DOMFormData> create()
47
    {
48
        return adoptRef(new DOMFormData());
49
    }
50
    static PassRefPtr<DOMFormData> create(const FormDataList& list)
51
    {
52
        return adoptRef(new DOMFormData(list));
53
    }
54
55
    void append(const String& name, const String& value);
56
    void append(const String& name, Blob* blob);
57
58
    const FormDataList& list() const { return m_list; }
59
60
private:
61
    DOMFormData();
62
    DOMFormData(const FormDataList& list);
63
64
    FormDataList m_list;
65
};
66
67
} // namespace WebCore
68
69
#endif // DOMFormData_h
- a/WebCore/xml/XMLHttpRequest.cpp +20 lines
Lines 26-31 a/WebCore/xml/XMLHttpRequest.cpp_sec1
26
#include "Cache.h"
26
#include "Cache.h"
27
#include "CString.h"
27
#include "CString.h"
28
#include "CrossOriginAccessControl.h"
28
#include "CrossOriginAccessControl.h"
29
#include "DOMFormData.h"
29
#include "DOMImplementation.h"
30
#include "DOMImplementation.h"
30
#include "Document.h"
31
#include "Document.h"
31
#include "Event.h"
32
#include "Event.h"
Lines 450-455 void XMLHttpRequest::send(Blob* body, ExceptionCode& ec) a/WebCore/xml/XMLHttpRequest.cpp_sec2
450
    createRequest(ec);
451
    createRequest(ec);
451
}
452
}
452
453
454
void XMLHttpRequest::send(DOMFormData* body, ExceptionCode& ec)
455
{
456
    if (!initSend(ec))
457
        return;
458
459
    if (m_method != "GET" && m_method != "HEAD" && m_url.protocolInHTTPFamily()) {
460
        m_requestEntityBody = FormData::create(*body, true, document());
461
462
        String contentType = getRequestHeader("Content-Type");
463
        if (contentType.isEmpty()) {
464
            contentType = "multipart/form-data; boundary=";
465
            contentType += m_requestEntityBody->boundary().data();
466
            setRequestHeaderInternal("Content-Type", contentType);
467
        }
468
    }
469
470
    createRequest(ec);
471
}
472
453
void XMLHttpRequest::createRequest(ExceptionCode& ec)
473
void XMLHttpRequest::createRequest(ExceptionCode& ec)
454
{
474
{
455
    // The presence of upload event listeners forces us to use preflighting because POSTing to an URL that does not
475
    // The presence of upload event listeners forces us to use preflighting because POSTing to an URL that does not
- a/WebCore/xml/XMLHttpRequest.h +2 lines
Lines 35-40 namespace WebCore { a/WebCore/xml/XMLHttpRequest.h_sec1
35
35
36
class Blob;
36
class Blob;
37
class Document;
37
class Document;
38
class DOMFormData;
38
class ResourceRequest;
39
class ResourceRequest;
39
class TextResourceDecoder;
40
class TextResourceDecoder;
40
class ThreadableLoader;
41
class ThreadableLoader;
Lines 73-78 public: a/WebCore/xml/XMLHttpRequest.h_sec2
73
    void send(Document*, ExceptionCode&);
74
    void send(Document*, ExceptionCode&);
74
    void send(const String&, ExceptionCode&);
75
    void send(const String&, ExceptionCode&);
75
    void send(Blob*, ExceptionCode&);
76
    void send(Blob*, ExceptionCode&);
77
    void send(DOMFormData*, ExceptionCode&);
76
    void abort();
78
    void abort();
77
    void setRequestHeader(const AtomicString& name, const String& value, ExceptionCode&);
79
    void setRequestHeader(const AtomicString& name, const String& value, ExceptionCode&);
78
    void overrideMimeType(const String& override);
80
    void overrideMimeType(const String& override);

Return to Bug 35707