Fixes #11 Segmentation fault.

This commit is contained in:
Miao Jiang 2013-02-20 02:58:50 +08:00
parent 01dbe4e0ce
commit 745124ebd6
4 changed files with 39 additions and 19 deletions

View file

@ -20,13 +20,14 @@ curl.on('data', function(chunk) {
curl.on('error', function(e) { curl.on('error', function(e) {
p("error: " + e.message) p("error: " + e.message)
curl.close(); curl.close();
once();
}); });
curl.on('end', function() { curl.on('end', function() {
p('done.'); curl.getinfo('RESPONSE_CODE');
p('code: ' + curl.getinfo('RESPONSE_CODE'));
curl.close(); curl.close();
p('done.');
}); });
curl.perform(); curl.perform();

View file

@ -1,6 +1,6 @@
// Generated by ToffeeScript 1.4.0 // Generated by ToffeeScript 1.4.0
(function() { (function() {
var Curl, m, p; var Curl, curls, id, m, p;
try { try {
Curl = require(__dirname + '/../build/Release/node-curl').Curl; Curl = require(__dirname + '/../build/Release/node-curl').Curl;
@ -8,6 +8,10 @@
Curl = require(__dirname + '/../build/default/node-curl').Curl; Curl = require(__dirname + '/../build/default/node-curl').Curl;
} }
curls = {};
id = 0;
Curl.prototype.setopt_user_ = function(option_id, value) { Curl.prototype.setopt_user_ = function(option_id, value) {
return this.options[option_id] = value; return this.options[option_id] = value;
}; };
@ -54,15 +58,26 @@
}; };
Curl.prototype.on = function(event, callback) { Curl.prototype.on = function(event, callback) {
var _this = this;
switch (event) { switch (event) {
case 'data': case 'data':
this.on_write = callback; this.on_write = callback;
break; break;
case 'error': case 'error':
this.on_error = callback; this.on_error = function() {
var rt;
rt = callback();
curls[_this.id] = null;
return rt;
};
break; break;
case 'end': case 'end':
this.on_end = callback; this.on_end = function() {
var rt;
rt = callback();
curls[_this.id] = null;
return rt;
};
break; break;
default: default:
throw new Error("invalid event type " + event); throw new Error("invalid event type " + event);
@ -71,6 +86,8 @@
}; };
Curl.prototype.perform = function() { Curl.prototype.perform = function() {
this.id = ++id;
curls[this.id] = this;
this.perform_(); this.perform_();
Curl.process(); Curl.process();
return this; return this;
@ -95,7 +112,7 @@
return process.nextTick(once); return process.nextTick(once);
} else { } else {
m = 0; m = 0;
w = (8192 - n) * 80 / 8192; w = (8192 - n) * 80 / 8192 >> 0;
if (w < 0) { if (w < 0) {
w = 0; w = 0;
} }

View file

@ -3,6 +3,8 @@ try
catch e catch e
{Curl} = require __dirname + '/../build/default/node-curl' {Curl} = require __dirname + '/../build/default/node-curl'
curls = {}
id = 0
Curl::setopt_user_ = (option_id, value) -> Curl::setopt_user_ = (option_id, value) ->
@options[option_id] = value @options[option_id] = value
@ -50,15 +52,24 @@ Curl::on = (event, callback) ->
@on_write = callback @on_write = callback
when 'error' when 'error'
# (Error error) -> # (Error error) ->
@on_error = callback @on_error = =>
rt = callback()
curls[@id] = null
rt
when 'end' when 'end'
# () -> # () ->
@on_end = callback @on_end = =>
rt = callback()
curls[@id] = null
rt
else else
throw new Error("invalid event type #{event}") throw new Error("invalid event type #{event}")
@ @
Curl::perform = -> Curl::perform = ->
@id = ++id
curls[@id] = @
@perform_() @perform_()
Curl.process() Curl.process()
@ @
@ -77,7 +88,7 @@ Curl.process = ->
process.nextTick once process.nextTick once
else else
m = 0 m = 0
w = (8192 - n) * 80 / 8192 w = (8192 - n) * 80 / 8192 >> 0
if w < 0 if w < 0
w = 0 w = 0
setTimeout once, w setTimeout once, w

View file

@ -29,8 +29,6 @@ class NodeCurl
CURL * curl; CURL * curl;
v8::Persistent<v8::Object> handle; v8::Persistent<v8::Object> handle;
// keep the object alive when performing
v8::Persistent<v8::Object> refer;
bool in_curlm; bool in_curlm;
std::vector<curl_slist*> slists; std::vector<curl_slist*> slists;
std::map<int, std::string> strings; std::map<int, std::string> strings;
@ -331,8 +329,7 @@ class NodeCurl
else else
curl->on_error(&msg_copy); curl->on_error(&msg_copy);
curl->refer.Dispose(); // Handle should not released in curl.process, or will cause segment fault.
curl->refer.Clear();
} }
} }
} }
@ -343,12 +340,6 @@ class NodeCurl
static v8::Handle<v8::Value> perform(const v8::Arguments & args) static v8::Handle<v8::Value> perform(const v8::Arguments & args)
{ {
NodeCurl *curl = unwrap(args.This()); NodeCurl *curl = unwrap(args.This());
if (!curl->refer.IsEmpty())
return raise("The curl session is running, use curl.create() to create another session.");
curl->refer = v8::Persistent<v8::Object>::New(args.This());
CURLMcode code = curl_multi_add_handle(curlm, curl->curl); CURLMcode code = curl_multi_add_handle(curlm, curl->curl);
if (code != CURLM_OK) if (code != CURLM_OK)
{ {