Tolerate empty local in JS_DateParse(). Return early, and let the error that triggered the empty local propogate to whatever may catch it. - Rewrite to use early returns - Prefer As<>() when previously tested with Is*() Bug: chromium:1142688 Change-Id: Iffe11bb0d75f61a6bf42f39beb37c9cb2de157a0 Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/75790 Reviewed-by: Daniel Hosseinian <dhoss@chromium.org> Commit-Queue: Tom Sepez <tsepez@chromium.org>
diff --git a/fxjs/js_define.cpp b/fxjs/js_define.cpp index 352370f..2bc1284 100644 --- a/fxjs/js_define.cpp +++ b/fxjs/js_define.cpp
@@ -29,30 +29,29 @@ v8::Local<v8::Context> context = pIsolate->GetCurrentContext(); // Use the built-in object method. - v8::Local<v8::Value> v = - context->Global() - ->Get(context, fxv8::NewStringHelper(pIsolate, "Date")) - .ToLocalChecked(); - if (v->IsObject()) { - v8::Local<v8::Object> o = v->ToObject(context).ToLocalChecked(); - v = o->Get(context, fxv8::NewStringHelper(pIsolate, "parse")) - .ToLocalChecked(); - if (v->IsFunction()) { - v8::Local<v8::Function> funC = v8::Local<v8::Function>::Cast(v); - const int argc = 1; - v8::Local<v8::String> timeStr = - fxv8::NewStringHelper(pIsolate, str.AsStringView()); - v8::Local<v8::Value> argv[argc] = {timeStr}; - v = funC->Call(context, context->Global(), argc, argv).ToLocalChecked(); - if (v->IsNumber()) { - double date = v->ToNumber(context).ToLocalChecked()->Value(); - if (!std::isfinite(date)) - return date; - return FX_LocalTime(date); - } - } - } - return 0; + v8::MaybeLocal<v8::Value> maybe_value = + context->Global()->Get(context, fxv8::NewStringHelper(pIsolate, "Date")); + + v8::Local<v8::Value> value; + if (!maybe_value.ToLocal(&value) || !value->IsObject()) + return 0; + + v8::Local<v8::Object> obj = value.As<v8::Object>(); + maybe_value = obj->Get(context, fxv8::NewStringHelper(pIsolate, "parse")); + if (!maybe_value.ToLocal(&value) || !value->IsFunction()) + return 0; + + v8::Local<v8::Function> func = value.As<v8::Function>(); + static constexpr int argc = 1; + v8::Local<v8::Value> argv[argc] = { + fxv8::NewStringHelper(pIsolate, str.AsStringView()), + }; + maybe_value = func->Call(context, context->Global(), argc, argv); + if (!maybe_value.ToLocal(&value) || !value->IsNumber()) + return 0; + + double date = value.As<v8::Number>()->Value(); + return std::isfinite(date) ? FX_LocalTime(date) : date; } std::vector<v8::Local<v8::Value>> ExpandKeywordParams(
diff --git a/testing/resources/javascript/bug_1142688.in b/testing/resources/javascript/bug_1142688.in new file mode 100644 index 0000000..6d3825d --- /dev/null +++ b/testing/resources/javascript/bug_1142688.in
@@ -0,0 +1,78 @@ +{{header}} +{{object 1 0}} << + /Type /Catalog + /Pages 5 0 R + /AcroForm << + /Fields [ + 3 0 R + 2 0 R + ] + >> +>> +endobj +{{object 2 0}} << + /Type /Annot + /Subtype /Widget + /FT /Tx + /T (tf1) +>> +endobj +{{object 3 0}} << + /Type /Annot + /Subtype /Widget + /FT /Tx + /T (tf0) + /AA << + /F 10 0 R + >> +>> +endobj +{{object 5 0}} << + /Type /Pages + /Count 2 + /Kids [ + 8 0 R + 9 0 R + ] +>> +endobj +{{object 8 0}} << + /Type /Page + /Parent 5 0 R + /Annots [3 0 R] +>> +endobj +{{object 9 0}} << + /Type /Page + /Parent 5 0 R + /Annots [2 0 R] +>> +endobj +{{object 10 0}} << + /Type /Action + /S /JavaScript + /JS 13 0 R +>> +{{object 13 0}} << + {{streamlen}} +>> +stream +function f3() { + // Setup dubious values in event recorder. + try { AFSpecial_Format(2); } catch(e) {} + try { AFNumber_Format(-302907477,0,1,-6,"",true); } catch(e) {} + + // Exhaust call stack, then do work upon exiting each frame. The + // objective is to get any call() made under the covers to throw + // with a stack size exception. + try { f3(); } catch(e) {} + try { AFDate_Keystroke("yymm-dd"); } catch(e) {} +} +f3(); +app.alert('Done.'); +endstream +endobj +{{xref}} +{{trailer}} +{{startxref}} +%%EOF
diff --git a/testing/resources/javascript/bug_1142688_expected.txt b/testing/resources/javascript/bug_1142688_expected.txt new file mode 100644 index 0000000..7cb32ca --- /dev/null +++ b/testing/resources/javascript/bug_1142688_expected.txt
@@ -0,0 +1 @@ +Alert: Done.