The data contained in this repository can be downloaded to your computer using one of several clients.
Please see the documentation of your version control software client for more information.

Please select the desired protocol below to get the URL.

This URL has Read-Only access.

Statistics
| Branch: | Revision:

main_repo / src / node.cc @ 90fc8d36

History | View | Annotate | Download (5.29 KB)

1
#include "node.h"
2

    
3
#include "net.h"
4
#include "file.h"
5
#include "process.h"
6
#include "http.h"
7
#include "timers.h"
8

    
9
#include "natives.h" 
10

    
11
#include <stdio.h>
12
#include <assert.h>
13

    
14
#include <string>
15
#include <list>
16
#include <map>
17

    
18
using namespace v8;
19
using namespace node;
20
using namespace std;
21

    
22
static int exit_code = 0;
23

    
24
// Extracts a C string from a V8 Utf8Value.
25
const char*
26
ToCString(const v8::String::Utf8Value& value)
27
{
28
  return *value ? *value : "<string conversion failed>";
29
}
30

    
31
void
32
ReportException(v8::TryCatch* try_catch)
33
{
34
  v8::HandleScope handle_scope;
35
  v8::String::Utf8Value exception(try_catch->Exception());
36
  const char* exception_string = ToCString(exception);
37
  v8::Handle<v8::Message> message = try_catch->Message();
38
  if (message.IsEmpty()) {
39
    // V8 didn't provide any extra information about this error; just
40
    // print the exception.
41
    printf("%s\n", exception_string);
42
  } else {
43
    message->PrintCurrentStackTrace(stdout);
44

    
45
    // Print (filename):(line number): (message).
46
    v8::String::Utf8Value filename(message->GetScriptResourceName());
47
    const char* filename_string = ToCString(filename);
48
    int linenum = message->GetLineNumber();
49
    printf("%s:%i: %s\n", filename_string, linenum, exception_string);
50
    // Print line of source code.
51
    v8::String::Utf8Value sourceline(message->GetSourceLine());
52
    const char* sourceline_string = ToCString(sourceline);
53
    printf("%s\n", sourceline_string);
54
    // Print wavy underline (GetUnderline is deprecated).
55
    int start = message->GetStartColumn();
56
    for (int i = 0; i < start; i++) {
57
      printf(" ");
58
    }
59
    int end = message->GetEndColumn();
60
    for (int i = start; i < end; i++) {
61
      printf("^");
62
    }
63
    printf("\n");
64
  }
65
}
66

    
67
// Executes a string within the current v8 context.
68
Handle<Value>
69
ExecuteString(v8::Handle<v8::String> source,
70
              v8::Handle<v8::Value> filename)
71
{
72
  HandleScope scope;
73
  TryCatch try_catch;
74

    
75
  Handle<Script> script = Script::Compile(source, filename);
76
  if (script.IsEmpty()) {
77
    ReportException(&try_catch);
78
    exit(1);
79
  }
80

    
81
  Handle<Value> result = script->Run();
82
  if (result.IsEmpty()) {
83
    ReportException(&try_catch);
84
    exit(1);
85
  }
86

    
87
  return scope.Close(result);
88
}
89

    
90
NODE_METHOD(compile) 
91
{
92
  if (args.Length() < 2) 
93
    return Undefined();
94

    
95
  HandleScope scope;
96

    
97
  Local<String> source = args[0]->ToString();
98
  Local<String> filename = args[1]->ToString();
99

    
100
  Handle<Value> result = ExecuteString(source, filename);
101
  
102
  return scope.Close(result);
103
}
104

    
105
NODE_METHOD(debug) 
106
{
107
  if (args.Length() < 1) 
108
    return Undefined();
109
  HandleScope scope;
110
  String::Utf8Value msg(args[0]->ToString());
111
  fprintf(stderr, "DEBUG: %s\n", *msg);
112
  return Undefined();
113
}
114

    
115
static void
116
OnFatalError (const char* location, const char* message)
117
{
118
#define FATAL_ERROR "\033[1;31mV8 FATAL ERROR.\033[m"
119
  if (location)
120
    fprintf(stderr, FATAL_ERROR " %s %s\n", location, message);
121
  else 
122
    fprintf(stderr, FATAL_ERROR " %s\n", message);
123

    
124
  exit(1);
125
}
126

    
127

    
128
void
129
node_fatal_exception (TryCatch &try_catch)
130
{
131
  ReportException(&try_catch);
132
  ev_unloop(EV_DEFAULT_UC_ EVUNLOOP_ALL);
133
  exit_code = 1;
134
}
135

    
136
void node_exit (int code)
137
{
138
  exit_code = code;
139
  ev_unloop(EV_DEFAULT_UC_ EVUNLOOP_ALL);
140
}
141

    
142

    
143
static ev_async thread_pool_watcher;
144

    
145
static void 
146
thread_pool_cb (EV_P_ ev_async *w, int revents)
147
{
148
  int r = eio_poll();
149
  /* returns 0 if all requests were handled, -1 if not, or the value of EIO_FINISH if != 0 */
150

    
151
  // XXX is this check too heavy? 
152
  //  it require three locks in eio
153
  //  what's the better way?
154
  if (eio_nreqs () == 0 && eio_nready() == 0 && eio_npending() == 0) 
155
    ev_async_stop(EV_DEFAULT_ w);
156
}
157

    
158
static void
159
thread_pool_want_poll (void)
160
{
161
  ev_async_send(EV_DEFAULT_ &thread_pool_watcher); 
162
}
163

    
164
void
165
node_eio_warmup (void)
166
{
167
  ev_async_start(EV_DEFAULT_ &thread_pool_watcher);
168
}
169

    
170
int
171
main (int argc, char *argv[]) 
172
{
173
  ev_default_loop(EVFLAG_AUTO); // initialize the default ev loop.
174

    
175
  // start eio thread pool
176
  ev_async_init(&thread_pool_watcher, thread_pool_cb);
177
  eio_init(thread_pool_want_poll, NULL);
178

    
179
  V8::SetFlagsFromCommandLine(&argc, argv, true);
180

    
181
  if(argc < 2)  {
182
    fprintf(stderr, "No script was specified.\n");
183
    return 1;
184
  }
185

    
186
  string filename(argv[1]);
187

    
188
  HandleScope handle_scope;
189

    
190
  Persistent<Context> context = Context::New(NULL, ObjectTemplate::New());
191
  Context::Scope context_scope(context);
192
  V8::SetFatalErrorHandler(OnFatalError);
193

    
194
  Local<Object> g = Context::GetCurrent()->Global();
195

    
196
  Local<Object> node = Object::New();
197
  g->Set(String::New("node"), node);
198

    
199
  NODE_SET_METHOD(node, "compile", compile);
200
  NODE_SET_METHOD(node, "debug", debug);
201

    
202
  Local<Array> arguments = Array::New(argc);
203
  for (int i = 0; i < argc; i++) {
204
    Local<String> arg = String::New(argv[i]);
205
    arguments->Set(Integer::New(i), arg);
206
  }
207
  g->Set(String::New("ARGV"), arguments);
208

    
209
  // BUILT-IN MODULES
210
  NodeInit_net(g);
211
  NodeInit_timers(g);
212
  NodeInit_process(g);
213
  NodeInit_file(g);
214
  NodeInit_http(g);
215

    
216
  // NATIVE JAVASCRIPT MODULES
217
  TryCatch try_catch;
218

    
219
  ExecuteString(String::New(native_file), String::New("file.js"));
220
  if (try_catch.HasCaught()) goto native_js_error; 
221

    
222
  ExecuteString(String::New(native_main), String::New("main.js"));
223
  if (try_catch.HasCaught()) goto native_js_error; 
224

    
225
  ev_loop(EV_DEFAULT_UC_ 0);
226

    
227
  context.Dispose();
228

    
229
  return exit_code;
230

    
231
native_js_error:
232
  ReportException(&try_catch);
233
  return 1;
234
}