[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [Gnash-commit] /srv/bzr/gnash/trunk r9754: Allow XML.sendAndLoad to
From: |
Benjamin Wolsey |
Subject: |
Re: [Gnash-commit] /srv/bzr/gnash/trunk r9754: Allow XML.sendAndLoad to take any object as second argument (tested in |
Date: |
Tue, 16 Sep 2008 16:10:58 +0200 |
> Diff too large for email (1050 lines, the limit is 1000).
This is annoying!
I would like all my commits to be easily reviewable, and I don't think
1000 lines is too much to include, particularly as an attachment.
I'm pasting a diff of that commit below for info, and voting for the
limit to be raised significantly.
bwy
=== modified file 'libbase/Makefile.am'
--- libbase/Makefile.am 2008-09-11 22:51:32 +0000
+++ libbase/Makefile.am 2008-09-16 12:36:54 +0000
@@ -150,7 +150,7 @@
WallClockTimer.h \
utf8.h \
utility.h \
- curl_adapter.h \
+ NetworkAdapter.h \
noseek_fd_adapter.h \
zlib_adapter.h \
URL.h \
=== renamed file 'libbase/curl_adapter.h' => 'libbase/NetworkAdapter.h'
--- libbase/curl_adapter.h 2008-06-12 11:12:46 +0000
+++ libbase/NetworkAdapter.h 2008-09-16 12:36:54 +0000
@@ -16,20 +16,25 @@
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
02110-1301 USA
-#ifndef CURL_ADAPTER_H
-#define CURL_ADAPTER_H
+#ifndef NETWORK_ADAPTER_H
+#define NETWORK_ADAPTER_H
#include "dsodefs.h"
+#include <map>
#include <string>
-
+#include "StringPredicates.h"
namespace gnash {
class IOChannel;
-
/// Code to use libcurl as an IOChannel stream.
-namespace curl_adapter {
+namespace NetworkAdapter {
+
+/// Custom headers for addRequestHeader. These are case insensitive,
and
+/// subsequent addition of a header already there replaces any previous
one.
+/// Some values are not allowed.
+typedef std::map<std::string, std::string, StringNoCaseLessThen>
RequestHeaders;
/// \brief
/// Returns a read-only IOChannel that fetches data
@@ -53,7 +58,10 @@
///
DSOEXPORT IOChannel* make_stream(const char* url, const std::string&
postdata);
-} // namespace gnash::curl_adaptar
+DSOEXPORT IOChannel* makeStream(const std::string& url, const
std::string& postdata,
+ const RequestHeaders& headers);
+
+}
} // namespace gnash
#endif // CURL_ADAPTER_H
=== modified file 'libbase/curl_adapter.cpp'
--- libbase/curl_adapter.cpp 2008-09-04 11:15:51 +0000
+++ libbase/curl_adapter.cpp 2008-09-16 12:36:54 +0000
@@ -1,4 +1,4 @@
-// curl_adapter.cpp: Interface to libcurl to read HTTP streams, for
Gnash.
+// NetworkAdapter.cpp: Interface to libcurl to read HTTP streams, for
Gnash.
//
// Copyright (C) 2005, 2006, 2007, 2008 Free Software Foundation,
Inc.
//
@@ -25,9 +25,9 @@
#include <pthread.h>
#endif
+#include "NetworkAdapter.h"
#include "utility.h" // UNUSED macro
#include "IOChannel.h"
-#include "curl_adapter.h"
#include "log.h"
#include "WallClockTimer.h"
@@ -42,15 +42,26 @@
#ifndef USE_CURL
// Stub for warning about access when no libcurl is defined.
-namespace curl_adapter
+namespace NetworkAdapter
{
IOChannel* make_stream(const char * /*url */)
{
log_error(_("ERROR: libcurl is not available, but "
"Gnash has attempted to use the curl adapter"));
- // Should abort instead?
return NULL;
}
+
+ IOChannel* make_stream(const char* url, const std::string&
postdata)
+ {
+ return make_stream(url);
+ }
+
+ IOChannel* makeStream(const std::string& url, const std::string&
postdata,
+ const RequestHeaders& headers)
+ {
+ return make_stream(url);
+ }
+
}
#else // def USE_CURL
@@ -83,7 +94,7 @@
namespace gnash {
-namespace curl_adapter {
+namespace NetworkAdapter {
/***********************************************************************
*
@@ -364,6 +375,9 @@
/// The url-encoded post data.
///
CurlStreamFile(const std::string& url, const std::string& vars);
+
+ CurlStreamFile(const std::string& url, const std::string& vars,
+ const NetworkAdapter::RequestHeaders& headers);
~CurlStreamFile();
@@ -889,6 +903,61 @@
}
/*public*/
+CurlStreamFile::CurlStreamFile(const std::string& url, const
std::string& vars, const NetworkAdapter::RequestHeaders& headers)
+{
+ log_debug("CurlStreamFile %p created", this);
+ init(url);
+
+ curl_slist *headerList = 0;
+
+ for (NetworkAdapter::RequestHeaders::const_iterator i =
headers.begin(),
+ e = headers.end(); i != e; ++i)
+ {
+ std::ostringstream os;
+ os << i->first << ": " << i->second;
+ headerList = curl_slist_append(headerList, os.str().c_str());
+ }
+
+ curl_easy_setopt(_handle, CURLOPT_HTTPHEADER, headerList);
+
+// curl_slist_free_all(headerList);
+
+ _postdata = vars;
+
+ CURLcode ccode;
+
+ ccode = curl_easy_setopt(_handle, CURLOPT_POST, 1);
+ if ( ccode != CURLE_OK ) {
+ throw gnash::GnashException(curl_easy_strerror(ccode));
+ }
+
+ // libcurl needs to access the POSTFIELDS during 'perform' operations,
+ // so we must use a string whose lifetime is ensured to be longer then
+ // the multihandle itself.
+ // The _postdata member should meet this requirement
+ ccode = curl_easy_setopt(_handle, CURLOPT_POSTFIELDS,
_postdata.c_str());
+ if ( ccode != CURLE_OK ) {
+ throw gnash::GnashException(curl_easy_strerror(ccode));
+ }
+
+ // This is to support binary strings as postdata
+ // NOTE: in version 7.11.1 CURLOPT_POSTFIELDSIZE_LARGE was added
+ // this one takes a long, that one takes a curl_off_t
+ //
+ ccode = curl_easy_setopt(_handle, CURLOPT_POSTFIELDSIZE,
_postdata.size());
+ if ( ccode != CURLE_OK ) {
+ throw gnash::GnashException(curl_easy_strerror(ccode));
+ }
+
+ CURLMcode mcode = curl_multi_add_handle(_mhandle, _handle);
+ if ( mcode != CURLM_OK ) {
+ throw gnash::GnashException(curl_multi_strerror(mcode));
+ }
+
+}
+
+
+/*public*/
CurlStreamFile::~CurlStreamFile()
{
log_debug("CurlStreamFile %p deleted", this);
@@ -1040,7 +1109,7 @@
}
if (std::fseek(_cache, 0, SEEK_END) == -1) {
- throw gnash::IOException("curl_adapter: fseek to end failed");
+ throw gnash::IOException("NetworkAdapter: fseek to end failed");
//gnash::log_error("Warning: fseek to end failed");
//return -1;
}
@@ -1214,7 +1283,25 @@
return stream;
}
-} // namespace curl_adapter
+DSOEXPORT IOChannel* makeStream(const std::string& url, const
std::string& postdata,
+ const RequestHeaders& headers)
+{
+
+ std::auto_ptr<CurlStreamFile> stream;
+
+ try {
+ stream.reset(new CurlStreamFile(url, postdata, headers));
+ }
+ catch (const std::exception& ex) {
+ gnash::log_error("curl stream: %s", ex.what());
+ }
+
+ return stream.release();
+
+}
+
+
+} // namespace NetworkAdapter
} // namespace gnash
#endif // def USE_CURL
=== modified file 'libcore/StreamProvider.cpp'
--- libcore/StreamProvider.cpp 2008-08-18 23:53:04 +0000
+++ libcore/StreamProvider.cpp 2008-09-16 12:36:54 +0000
@@ -29,10 +29,7 @@
#include "StreamProvider.h"
#include "URL.h"
#include "tu_file.h"
-#ifdef USE_CURL
-//# include <curl/curl.h>
-# include "curl_adapter.h"
-#endif
+#include "NetworkAdapter.h"
#include "URLAccessManager.h"
#include "log.h"
#include "rc.h" // for rcfile
@@ -63,7 +60,6 @@
IOChannel*
StreamProvider::getStream(const URL& url)
{
-// GNASH_REPORT_FUNCTION;
if (url.protocol() == "file")
{
@@ -93,26 +89,40 @@
}
else
{
-#ifdef USE_CURL
std::string url_str = url.str();
const char* c_url = url_str.c_str();
if ( URLAccessManager::allow(url) ) {
- return curl_adapter::make_stream(c_url);
+ return NetworkAdapter::make_stream(c_url);
} else {
return NULL;
}
-#else
- log_error(_("Unsupported network connection %s"),
- url.str().c_str());
- return NULL;
-#endif
- }
+ }
+}
+
+std::auto_ptr<IOChannel>
+StreamProvider::getStream(const URL& url, const std::string& postdata,
+ const NetworkAdapter::RequestHeaders&
headers)
+{
+ if (url.protocol() == "file")
+ {
+ log_error("Request Headers discarded while getting stream from
file: uri");
+ return std::auto_ptr<IOChannel>(getStream(url, postdata));
+ }
+
+ std::auto_ptr<IOChannel> ret;
+
+ std::string url_str = url.str();
+ const char* c_url = url_str.c_str();
+ if ( URLAccessManager::allow(url) ) {
+ ret.reset(NetworkAdapter::makeStream(c_url, postdata, headers));
+ }
+ return ret;
+
}
IOChannel*
StreamProvider::getStream(const URL& url, const std::string& postdata)
{
-// GNASH_REPORT_FUNCTION;
if (url.protocol() == "file")
{
@@ -135,19 +145,13 @@
}
else
{
-#ifdef USE_CURL
std::string url_str = url.str();
const char* c_url = url_str.c_str();
if ( URLAccessManager::allow(url) ) {
- return curl_adapter::make_stream(c_url, postdata);
+ return NetworkAdapter::make_stream(c_url, postdata);
} else {
return NULL;
}
-#else
- log_error(_("Unsupported network connection %s"),
- url.str().c_str());
- return NULL;
-#endif
}
}
=== modified file 'libcore/StreamProvider.h'
--- libcore/StreamProvider.h 2008-06-09 13:31:51 +0000
+++ libcore/StreamProvider.h 2008-09-16 12:36:54 +0000
@@ -15,10 +15,12 @@
// along with this program; if not, write to the Free Software
// Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
02110-1301 USA
-#ifndef _GNASH_STREAMPROVIDER_H
-#define _GNASH_STREAMPROVIDER_H
+#ifndef GNASH_STREAMPROVIDER_H
+#define GNASH_STREAMPROVIDER_H
-#include <string>
+#include <map>
+#include <memory>
+#include "NetworkAdapter.h"
// Forward declarations
namespace gnash {
@@ -64,6 +66,9 @@
///
virtual IOChannel* getStream(const URL& url, const std::string&
postdata);
+ virtual std::auto_ptr<IOChannel> getStream(const URL& url,
+ const std::string& postdata, const
NetworkAdapter::RequestHeaders& headers);
+
};
} // namespace gnash
=== modified file 'libcore/as_object.h'
--- libcore/as_object.h 2008-09-12 10:37:09 +0000
+++ libcore/as_object.h 2008-09-16 12:36:54 +0000
@@ -47,6 +47,7 @@
class as_environment;
class VM;
class Machine;
+ class IOChannel;
}
namespace gnash {
@@ -221,6 +222,10 @@
/// to a string.
virtual bool useCustomToString() const { return true; }
+ /// Loads data from an IOChannel. The default implementation
+ /// does nothing.
+ virtual void queueLoad(std::auto_ptr<IOChannel> /*str*/) {};
+
/// Return the numeric value of this object
//
/// The default implementation converts the text value
=== modified file 'libcore/asobj/LoadVars.cpp'
--- libcore/asobj/LoadVars.cpp 2008-08-25 13:48:20 +0000
+++ libcore/asobj/LoadVars.cpp 2008-09-16 12:36:55 +0000
@@ -95,6 +95,8 @@
///
void sendAndLoad(const std::string& urlstr, LoadVars& target, bool
post=true);
+ void queueLoad(std::auto_ptr<IOChannel> str);
+
static as_object* getLoadVarsInterface();
static void attachLoadVarsInterface(as_object& o);
@@ -331,23 +333,37 @@
URL url(urlstr, get_base_url());
std::auto_ptr<IOChannel> str;
- if ( postdata ) str.reset
( StreamProvider::getDefaultInstance().getStream(url,
std::string(postdata)) );
- else str.reset
( StreamProvider::getDefaultInstance().getStream(url) );
+ if ( postdata )
+ {
+ str.reset (StreamProvider::getDefaultInstance().getStream(
+ url, std::string(postdata)) );
+ }
+ else
+ {
+ str.reset
(StreamProvider::getDefaultInstance().getStream(url));
+ }
- if ( ! str.get() )
+ if (!str.get())
{
- log_error(_("Can't load variables from %s (security?)"),
url.str().c_str());
+ log_error(_("Can't load variables from %s (security?)"),
url.str());
return;
// TODO: check if this is correct
//as_value nullValue; nullValue.set_null();
//callMethod(VM::get().getStringTable().find(PROPNAME("onData")),
nullValue);
}
- log_security(_("Loading variables file from url: '%s'"),
url.str().c_str());
+ log_security(_("Loading variables file from url: '%s'"), url.str());
+ queueLoad(str);
+
+}
+
+void
+LoadVars::queueLoad(std::auto_ptr<IOChannel> str)
+{
bool startTimer = _loadThreads.empty();
- std::auto_ptr<LoadThread> lt ( new LoadThread(str) );
+ std::auto_ptr<LoadThread> lt (new LoadThread(str));
// we push on the front to avoid invalidating
// iterators when queueLoad is called as effect
@@ -355,14 +371,14 @@
// Doing so also avoids processing queued load
// request immediately
//
- _loadThreads.push_front(lt.get());
+ _loadThreads.push_front(lt.release());
#ifdef DEBUG_LOADS
- log_debug("Pushed thread %p to _loadThreads, number of LoadVars load
threads now: %d", (void*)lt.get(), _loadThreads.size());
+ log_debug("Pushed thread %p to _loadThreads, number of "
+ "LoadVars load threads now: %d",
+ static_cast<void*>(_loadThreads.front()),
_loadThreads.size());
#endif
- lt.release();
-
-
- if ( startTimer )
+
+ if (startTimer)
{
boost::intrusive_ptr<builtin_function> loadsChecker =
new builtin_function(&LoadVars::checkLoads_wrapper);
@@ -373,9 +389,9 @@
log_debug("Registered LoadVars loads interval %d",
_loadCheckerTimer);
#endif
}
-
}
+
void
LoadVars::load(const std::string& urlstr)
{
=== modified file 'libcore/asobj/LoadVars.h'
--- libcore/asobj/LoadVars.h 2008-08-25 13:48:20 +0000
+++ libcore/asobj/LoadVars.h 2008-09-16 12:36:55 +0000
@@ -31,6 +31,5 @@
} // end of gnash namespace
-// __GNASH_ASOBJ_LOADVARS_H__
#endif
=== modified file 'libcore/asobj/xml.cpp'
--- libcore/asobj/xml.cpp 2008-08-29 14:29:54 +0000
+++ libcore/asobj/xml.cpp 2008-09-16 12:36:55 +0000
@@ -49,6 +49,7 @@
#include <vector>
#include <boost/algorithm/string/case_conv.hpp>
#include <memory>
+#include <functional> // std::make_pair
namespace gnash {
@@ -92,11 +93,10 @@
_bytesTotal(-1),
_bytesLoaded(-1)
{
- //GNASH_REPORT_FUNCTION;
#ifdef DEBUG_MEMORY_ALLOCATION
log_debug(_("Creating XML data at %p"), this);
#endif
- //log_debug("%s: %p", __FUNCTION__, this);
+
attachXMLProperties(*this);
}
@@ -114,10 +114,10 @@
_bytesTotal(-1),
_bytesLoaded(-1)
{
- //GNASH_REPORT_FUNCTION;
#ifdef DEBUG_MEMORY_ALLOCATION
log_debug(_("Creating XML data at %p"), this);
#endif
+
parseXML(xml_in);
}
@@ -366,13 +366,6 @@
void
XML::queueLoad(std::auto_ptr<IOChannel> str)
{
- //GNASH_REPORT_FUNCTION;
-
- // Set the "loaded" parameter to false
- VM& vm = getVM();
- string_table& st = vm.getStringTable();
- string_table::key loadedKey = st.find("loaded");
- set_member(loadedKey, as_value(false));
bool startTimer = _loadThreads.empty();
@@ -521,8 +514,9 @@
XML::load(const URL& url)
{
GNASH_REPORT_FUNCTION;
-
- //log_debug(_("%s: mem is %d"), __FUNCTION__, mem);
+
+ // Set a loaded property to false before starting the load.
+ set_member(NSV::PROP_LOADED, false);
std::auto_ptr<IOChannel> str
( StreamProvider::getDefaultInstance().getStream(url) );
if ( ! str.get() )
@@ -566,9 +560,10 @@
/// If multiple calls are made to set the same header name, each
/// successive value replaces the value set in the previous call.
void
-XML::addRequestHeader(const char * /* name */, const char * /* value
*/)
+XML::addRequestHeader(const NetworkAdapter::RequestHeaders::value_type&
headerPair)
{
- log_unimpl (__FUNCTION__);
+ /// Replace existing values.
+ _headers[headerPair.first] = headerPair.second;
}
@@ -578,10 +573,12 @@
log_unimpl (__FUNCTION__);
}
-bool
-XML::sendAndLoad(const URL& url, XML& target)
+void
+XML::sendAndLoad(const URL& url, as_object& target)
{
- //GNASH_REPORT_FUNCTION;
+
+ /// All objects get a loaded member, set to false.
+ target.set_member(NSV::PROP_LOADED, false);
std::stringstream ss;
toString(ss);
@@ -595,23 +592,32 @@
{
log_unimpl ("Custom ContentType (%s) in XML.sendAndLoad",
ctypeVal);
}
-
- //log_debug(_("%s: mem is %d"), __FUNCTION__, mem);
-
- std::auto_ptr<IOChannel> str
( StreamProvider::getDefaultInstance().getStream(url, data) );
- if ( ! str.get() )
+
+ std::auto_ptr<IOChannel> stream;
+
+ if (_headers.empty())
+ {
+
stream.reset(StreamProvider::getDefaultInstance().getStream(url, data));
+ }
+ else
+ {
+ log_debug("With headers");
+ stream = StreamProvider::getDefaultInstance().getStream(url,
data, _headers);
+ // Clear the headers for next send and load? Probably not.
+ }
+
+ if (!stream.get())
{
log_error(_("Can't load XML file: %s (security?)"), url.str());
- return false;
+ return;
// TODO: this is still not correct.. we should still send
onData later...
//as_value nullValue; nullValue.set_null();
//callMethod(NSV::PROP_ON_DATA, nullValue);
}
log_security(_("Loading XML file from url: '%s'"), url.str());
- target.queueLoad(str);
-
- return true;
+ target.queueLoad(stream);
+
}
@@ -697,9 +703,6 @@
{
as_value inum;
boost::intrusive_ptr<XML> xml_obj;
- //const char *data;
-
- // log_debug(_("%s: nargs=%d"), __FUNCTION__, fn.nargs);
if ( fn.nargs > 0 )
{
@@ -709,7 +712,7 @@
xml_obj = boost::dynamic_pointer_cast<XML>(obj);
if ( xml_obj )
{
- log_debug(_("\tCloned the XML object at %p"), (void
*)xml_obj.get());
+ log_debug(_("Cloned the XML object at %p"), (void
*)xml_obj.get());
return as_value(xml_obj->cloneNode(true).get());
}
}
@@ -735,22 +738,47 @@
return as_value(xml_obj.get());
}
-//
-// SWF Property of this class. These are "accessors" into the private
data
-// of the class.
-//
-
-as_value xml_addrequestheader(const fn_call& fn)
+/// Can take either a list of strings as arguments, alternately header
+/// and value, or an array.
+as_value
+xml_addrequestheader(const fn_call& fn)
{
+
GNASH_REPORT_FUNCTION;
- log_debug(_("%s: %d args"), __PRETTY_FUNCTION__, fn.nargs);
-
-// return as_value(ptr->getAllocated());
-// ptr->addRequestHeader();
- log_unimpl (__FUNCTION__);
+
+ boost::intrusive_ptr<XML> ptr = ensureType<XML>(fn.this_ptr);
+
+ std::ostringstream ss;
+ fn.dump_args(ss);
+ log_debug ("addRequestHeader: %s", ss.str());
+
+ if (fn.nargs == 0)
+ {
+ IF_VERBOSE_ASCODING_ERRORS(
+ log_aserror(_("XML.addRequestHeader requires at least one
argument"));
+ );
+ return as_value();
+ }
+
+ if (fn.nargs < 2)
+ {
+ // TODO: handle array.
+ log_unimpl(_("Array argument to XML.addRequestHeader"));
+ return as_value();
+ }
+
+ // TODO: should we ignore orphaned arguments like this?
+ for (size_t i = 0, e = fn.nargs / 2; i != e; ++i)
+ {
+ const std::string& name = fn.arg(i * 2).to_string();
+ const std::string& val = fn.arg(i * 2 + 1).to_string();
+ ptr->addRequestHeader(std::make_pair(name, val));
+ }
+
return as_value();
}
+
/// \brief create a new XML element
///
/// Method; creates a new XML element with the name specified in the
@@ -759,11 +787,9 @@
/// created XML object that represents the element. This method and
/// the XML.createTextNode() method are the constructor methods for
/// creating nodes for an XML object.
-
static as_value
xml_createelement(const fn_call& fn)
{
-// GNASH_REPORT_FUNCTION;
if (fn.nargs > 0) {
const std::string& text = fn.arg(0).to_string();
@@ -779,6 +805,7 @@
return as_value();
}
+
/// \brief Create a new XML node
///
/// Method; creates a new XML text node with the specified text. The
@@ -787,23 +814,21 @@
/// object that represents the new text node. This method and the
/// XML.createElement() method are the constructor methods for
/// creating nodes for an XML object.
-
as_value
xml_createtextnode(const fn_call& fn)
{
-// GNASH_REPORT_FUNCTION;
XMLNode *xml_obj;
if (fn.nargs > 0) {
- const std::string& text = fn.arg(0).to_string();
- xml_obj = new XMLNode;
- xml_obj->nodeValueSet(text);
- xml_obj->nodeTypeSet(XMLNode::tText);
- return as_value(xml_obj);
-// log_debug(_("%s: xml obj is %p"), __PRETTY_FUNCTION__, xml_obj);
- } else {
- log_error(_("no text for text node creation"));
+ const std::string& text = fn.arg(0).to_string();
+ xml_obj = new XMLNode;
+ xml_obj->nodeValueSet(text);
+ xml_obj->nodeTypeSet(XMLNode::tText);
+ return as_value(xml_obj);
+ }
+ else {
+ log_error(_("no text for text node creation"));
}
return as_value();
}
@@ -826,7 +851,7 @@
as_value xml_parsexml(const fn_call& fn)
{
- //GNASH_REPORT_FUNCTION;
+
as_value method;
as_value val;
boost::intrusive_ptr<XML> ptr = ensureType<XML>(fn.this_ptr);
@@ -847,17 +872,19 @@
/// \brief removes the specified XML object from its parent. Also
/// deletes all descendants of the node.
-
as_value xml_send(const fn_call& fn)
{
GNASH_REPORT_FUNCTION;
boost::intrusive_ptr<XML> ptr = ensureType<XML>(fn.this_ptr);
-// return as_value(ptr->getAllocated());
ptr->send();
return as_value();
}
+/// Returns true if the arguments are valid, otherwise false. The
+/// success of the connection is irrelevant.
+/// The second argument must be an object, but does not have to
+/// be an XML object.
static as_value
xml_sendandload(const fn_call& fn)
{
@@ -877,35 +904,26 @@
const std::string& filespec = fn.arg(0).to_string();
+ if (!fn.arg(1).is_object())
+ {
+ IF_VERBOSE_ASCODING_ERRORS(
+ std::ostringstream ss;
+ fn.dump_args(ss);
+ log_aserror(_("XML.sendAndLoad(%s): second argument is not "
+ "an object"), ss.str());
+ );
+
+ return as_value(false);
+ }
+
boost::intrusive_ptr<as_object> targetObj = fn.arg(1).to_object();
- if ( ! targetObj )
- {
- IF_VERBOSE_ASCODING_ERRORS(
- std::stringstream ss;
- fn.dump_args(ss);
- log_aserror(_("XML.sendAndLoad(%s): second argument doesn't
cast to an object"),
- ss.str());
- );
- return as_value(false);
- }
- XML* target = dynamic_cast<XML*>(targetObj.get());
- if ( ! target )
- {
- IF_VERBOSE_ASCODING_ERRORS(
- std::stringstream ss;
- fn.dump_args(ss);
- log_aserror(_("XML.sendAndLoad(%s): second argument is not an
XML object"),
- ss.str());
- );
- return as_value(false);
- }
+ assert(targetObj);
URL url(filespec, get_base_url());
-// return as_value(ptr->getAllocated());
- bool ret = ptr->sendAndLoad(url, *target);
+ ptr->sendAndLoad(url, *targetObj);
- return ret; // TODO: check expected return values
+ return as_value(true);
}
static as_value
@@ -942,12 +960,6 @@
return as_value();
}
-int
-memadjust(int x)
-{
- return (x + (4 - x % 4));
-}
-
// extern (used by Global.cpp)
void xml_class_init(as_object& global)
{
=== modified file 'libcore/asobj/xml.h'
--- libcore/asobj/xml.h 2008-08-29 14:29:54 +0000
+++ libcore/asobj/xml.h 2008-09-16 12:36:55 +0000
@@ -24,6 +24,7 @@
#include "xmlnode.h"
#include "log.h"
#include "dsodefs.h"
+#include "NetworkAdapter.h"
#include <vector>
#include <sstream>
@@ -131,12 +132,11 @@
XMLNode *processNode(xmlTextReaderPtr reader, XMLNode *node);
- void change_stack_frame(int frame, gnash::as_object *xml,
gnash::as_environment *env);
-
- void cleanupStackFrames( XMLNode *data);
-
- // These 6 have to
- void addRequestHeader(const char *name, const char *value);
+ void change_stack_frame(int frame, gnash::as_object *xml,
gnash::as_environment *env);
+
+ void cleanupStackFrames( XMLNode *data);
+
+ void addRequestHeader(const
NetworkAdapter::RequestHeaders::value_type&);
XMLNode *createElement(const char *name);
@@ -144,7 +144,8 @@
void send();
- bool sendAndLoad(const URL& url, XML& target);
+ /// ActionScript doesn't care about the success of the connection.
+ void sendAndLoad(const URL& url, as_object& target);
/// @return -1 if no loaded was started yet
long int getBytesLoaded() const;
@@ -222,6 +223,9 @@
long int _bytesTotal;
long int _bytesLoaded;
+
+ NetworkAdapter::RequestHeaders _headers;
+
};
=== modified file 'testsuite/actionscript.all/XML.as'
--- testsuite/actionscript.all/XML.as 2008-04-08 09:09:20 +0000
+++ testsuite/actionscript.all/XML.as 2008-09-16 12:36:56 +0000
@@ -26,12 +26,14 @@
//#include "dejagnu.as"
#include "utils.as"
+#if OUTPUT_VERSION < 6
+Object.prototype.hasOwnProperty = ASnative(101, 5);
+#endif
+
var existtests = true;
check(XML);
-#if OUTPUT_VERSION >= 6 // {
-
check(! XML.prototype.hasOwnProperty("appendChild") );
check(! XML.prototype.hasOwnProperty("cloneNode") );
check(! XML.prototype.hasOwnProperty("hasChildNodes") );
@@ -102,8 +104,6 @@
check(! XMLNode.hasOwnProperty("cloneNode") );
check(! XMLNode.hasOwnProperty("nodeValue"));
-#endif // OUTPUT_VERSION >= 6 }
-
check(XML.prototype instanceof XMLNode);
var tmp = new XML();
@@ -120,11 +120,7 @@
check_equals(typeof(tmp.status), 'number');
check(! tmp.hasOwnProperty("status"));
-#if OUTPUT_VERSION < 6
- check(! tmp.__proto__.hasOwnProperty('status') );
-#else
- xcheck(tmp.__proto__.hasOwnProperty('status') );
-#endif
+xcheck(tmp.__proto__.hasOwnProperty('status') );
check_equals(tmp.status, 0);
tmp.status = -1;
@@ -637,6 +633,62 @@
// #endif
+// Test sendAndLoad return;
+// Any object can be passed as second argument.
+
+x = new XML;
+r = new Object;
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), true);
+check(r.hasOwnProperty("loaded"));
+
+r = new XML;
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), true);
+check(!r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "boolean");
+check_equals(r.loaded, false);
+
+#if OUTPUT_VERSION > 5
+// No LoadVars in SWF 5.
+r = new LoadVars;
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), true);
+check(r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "boolean");
+check_equals(r.loaded, false);
+#endif
+
+r = new Date(1);
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), true);
+check(r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "boolean");
+check_equals(r.loaded, false);
+t = new Date(1);
+check_equals(r.toString(), t.toString());
+check(r instanceOf Date);
+
+r = 3;
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), false);
+check(!r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "undefined");
+check_equals(r.loaded, undefined);
+
+r = "string";
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), false);
+check(!r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "undefined");
+check_equals(r.loaded, undefined);
+
+r = {};
+check(!r.hasOwnProperty("loaded"));
+check_equals(x.sendAndLoad("some server name", r), true);
+check(r.hasOwnProperty("loaded"));
+check_equals(typeof(r.loaded), "boolean");
+check_equals(r.loaded, false);
//--------------------------------------------------------------------
// Test loading an XML locally
//--------------------------------------------------------------------
@@ -702,8 +754,13 @@
check_equals(myxml.nodeName, null);
topnode = myxml.firstChild;
+#if OUTPUT_VERSION == 5
+ xcheck_equals(topnode.nodeName, null);
+ xcheck_equals(topnode.attributes.attr1, undefined);
+#else
check_equals(topnode.nodeName, 'XML');
check_equals(topnode.attributes.attr1, 'attr1 value');
+#endif
// XML, comment, NULL
if ( typeof(myxml.lastChildNodesCount) == 'undefined' )
@@ -714,7 +771,11 @@
{
check_equals(myxml.childNodes.length,
myxml.lastChildNodesCount);
}
+#if OUTPUT_VERSION == 5
+ xcheck_equals(myxml.childNodes.length, 4); // gnash fails discarding
the comment and the ending blanks
+#else
check_equals(myxml.childNodes.length, 3); // gnash fails discarding
the comment and the ending blanks
+#endif
// We're done
++this.onLoadCalls;
@@ -722,9 +783,9 @@
if ( this.onLoadCalls == 2 )
{
#if OUTPUT_VERSION < 6
- check_totals(265);
+ check_totals(360);
#else
- check_totals(341);
+ check_totals(376);
#endif
play();
}
=== modified file 'testsuite/misc-ming.all/XMLSocketTest.c'
--- testsuite/misc-ming.all/XMLSocketTest.c 2008-08-25 15:16:42 +0000
+++ testsuite/misc-ming.all/XMLSocketTest.c 2008-09-16 12:41:21 +0000
@@ -35,7 +35,7 @@
SWFMovie mo;
const char* srcdir = ".";
- char longString[15000];
+ char longString[15001];
if ( argc>1 ) srcdir=argv[1];
else
@@ -126,6 +126,7 @@
strncpy(longString, "xmlArray[11] = '", 16);
longString[14998] = '\'';
longString[14999] = ';';
+ longString[15000] = 0;
add_actions(mo, longString);
signature.asc
Description: Dies ist ein digital signierter Nachrichtenteil