hotspot/src/share/vm/utilities/json.cpp
changeset 41335 27115e2e42cc
parent 35529 39376b4613b5
equal deleted inserted replaced
41334:8b28be7b8613 41335:27115e2e42cc
     1 /*
     1 /*
     2  * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved.
     2  * Copyright (c) 2015, 2016, Oracle and/or its affiliates. All rights reserved.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     4  *
     4  *
     5  * This code is free software; you can redistribute it and/or modify it
     5  * This code is free software; you can redistribute it and/or modify it
     6  * under the terms of the GNU General Public License version 2 only, as
     6  * under the terms of the GNU General Public License version 2 only, as
     7  * published by the Free Software Foundation.
     7  * published by the Free Software Foundation.
   684 
   684 
   685     _st->print_cr("%s", line_start);
   685     _st->print_cr("%s", line_start);
   686   }
   686   }
   687 }
   687 }
   688 
   688 
   689 #ifndef PRODUCT
       
   690 class JSONTest : public JSON {
       
   691  public:
       
   692   static void test();
       
   693 
       
   694  private:
       
   695   JSONTest(const char* text);
       
   696   static void test(const char* json, bool valid);
       
   697 
       
   698   void log(uint level, const char* format, ...) ATTRIBUTE_PRINTF(3, 4);
       
   699 
       
   700   bool callback(JSON_TYPE t, JSON_VAL* v, uint level);
       
   701   JSON_TYPE prev;
       
   702 };
       
   703 
       
   704 void JSON_test() {
       
   705   JSONTest::test();
       
   706 }
       
   707 
       
   708 void JSONTest::test(const char* text, bool should_pass) {
       
   709   JSONTest json(text);
       
   710   if (should_pass) {
       
   711     assert(json.valid() == true, "failed on a valid json string");
       
   712     if (VerboseInternalVMTests) {
       
   713       tty->print_cr("-- json test passed as expected --");
       
   714     }
       
   715   } else {
       
   716     assert(json.valid() == false, "succeeded on an invalid json string");
       
   717     if (VerboseInternalVMTests) {
       
   718       tty->print_cr("-- json test failed as expected --");
       
   719     }
       
   720   }
       
   721 }
       
   722 
       
   723 JSONTest::JSONTest(const char* text) : JSON(text, !VerboseInternalVMTests, tty) {
       
   724   prev = JSON_NONE;
       
   725   parse();
       
   726 }
       
   727 
       
   728 void JSONTest::test() {
       
   729   JSONTest::test("{}", true);
       
   730   JSONTest::test("[]", true);
       
   731   JSONTest::test("  {  }  ", true);
       
   732   JSONTest::test("  [  ]  ", true);
       
   733 
       
   734   JSONTest::test("\"error\"", false);
       
   735   JSONTest::test("error", false);
       
   736   JSONTest::test("1", false);
       
   737   JSONTest::test("1.2", false);
       
   738   JSONTest::test("true", false);
       
   739   JSONTest::test("false", false);
       
   740   JSONTest::test("null", false);
       
   741 
       
   742   JSONTest::test("[ 1 ]", true);
       
   743   JSONTest::test("[ 1, ]", true);
       
   744   JSONTest::test("[ true ]", true);
       
   745   JSONTest::test("[ true, ]", true);
       
   746   JSONTest::test("[ false ]", true);
       
   747   JSONTest::test("[ false, ]", true);
       
   748   JSONTest::test("[ null ]", true);
       
   749   JSONTest::test("[ null, ]", true);
       
   750   JSONTest::test("[ \"\" ]", true);
       
   751   JSONTest::test("[ \"\", ]", true);
       
   752   JSONTest::test("[ \"elem1\" ]", true);
       
   753   JSONTest::test("[ \"elem1\", ]", true);
       
   754   JSONTest::test("[ \"elem1\", ]", true);
       
   755   JSONTest::test("[ \"elem1\" ]", true);
       
   756   JSONTest::test("[ \"elem1\", \"elem2\" ]", true);
       
   757   JSONTest::test("[ \"elem1\", \"elem2\", ]", true);
       
   758 
       
   759 
       
   760   JSONTest::test("[ \"elem1\" ] { }", false);
       
   761   JSONTest::test("[ elem1, \"elem2\" ]", false);
       
   762   JSONTest::test("[ \"elem1\"", false);
       
   763   JSONTest::test("[ \"elem1 ]", false);
       
   764   JSONTest::test("[ \"elem1\", \"elem2\"", false);
       
   765   JSONTest::test("[ truefoo ]", false);
       
   766   JSONTest::test("[ falsefoo ]", false);
       
   767   JSONTest::test("[ nullfoo ]", false);
       
   768 
       
   769   JSONTest::test("{ key : 1 }", true);
       
   770   JSONTest::test("{ key : 1, }", true);
       
   771   JSONTest::test("{ key : true }", true);
       
   772   JSONTest::test("{ key : true, }", true);
       
   773   JSONTest::test("{ key : false }", true);
       
   774   JSONTest::test("{ key : false, }", true);
       
   775   JSONTest::test("{ key : null }", true);
       
   776   JSONTest::test("{ key : null, }", true);
       
   777   JSONTest::test("{ \"\" : \"\" }", true);
       
   778   JSONTest::test("{ \"\" : \"\", }", true);
       
   779   JSONTest::test("{ \"key1\" : \"val1\" }", true);
       
   780   JSONTest::test("{ \"key1\" : \"val1\", }", true);
       
   781   JSONTest::test("{ \"key1\" : \"val1\", \"key2\" : \"val2\" }", true);
       
   782   JSONTest::test("{ \"key1\" : \"val1\", \"key2\" : \"val2\", }", true);
       
   783 
       
   784   JSONTest::test("{ \"key\" : \"val\" } [ \"error\" ]", false);
       
   785   JSONTest::test("{ \"key\" : \"val\" ", false);
       
   786 
       
   787   JSONTest::test("/**/ { }", true);
       
   788   JSONTest::test("/* */ { }", true);
       
   789   JSONTest::test("/*foo*/ { }", true);
       
   790   JSONTest::test("/* *foo */ { }", true);
       
   791   JSONTest::test("/* *foo* */ { }", true);
       
   792   JSONTest::test("/* /*foo */ { }", true);
       
   793   JSONTest::test("{ } /* foo */", true);
       
   794   JSONTest::test("{ } /* foo */ ", true);
       
   795   JSONTest::test("{ } //", true);
       
   796   JSONTest::test("{ } // ", true);
       
   797   JSONTest::test("{ } // foo", true);
       
   798 
       
   799   JSONTest::test("/* * / { }", false);
       
   800   JSONTest::test("/ * */ { }", false);
       
   801   JSONTest::test("// { }", false);
       
   802   JSONTest::test("/* { } */", false);
       
   803   JSONTest::test("/* { } */ ", false);
       
   804   JSONTest::test("/* { } ", false);
       
   805   JSONTest::test("{ } /* ", false);
       
   806   JSONTest::test("/* { } *", false);
       
   807   JSONTest::test("{ /* } */", false);
       
   808   JSONTest::test("[ /* ] */", false);
       
   809   JSONTest::test("{ key : \"val\", /* } */", false);
       
   810   JSONTest::test("[ \"val\", /* ] */", false);
       
   811 
       
   812   JSONTest::test("/* comment */{ key1 : { \"key2\" : { \"key3\" : [ \"elem1\", \"elem2\", { \"key4\" : null }, 3 , 2 , 1 , 0 , -1 , -2 , -3 , true, false, null, ] }, \"key5\" : true }, \"key6\" : [ \"☃\" ], key7 : \"val\",}", true);
       
   813   JSONTest::test("/* comment */ { \"key1\" : { \"key2\" : { \"key3\" : [ \"elem1\", \"elem2\", { \"key4\" : null }, 3 , 2 , 1 , 0 , -1 , -2 , -3 , true, false, null, ] }, \"key5\" : true }, \"key6\" : [ \"☃\" ], key7 : \"val\",}", true);
       
   814   JSONTest::test("/*comment*/{\"ff1 fsd\":{\"☃\":{\"☃\":[\"☃\",\"☃\"]},\"☃\":true},\"☃\":[\"☃\"],\"foo\":\"☃\",}", true);
       
   815   JSONTest::test("/* comment */ { key1 error : { \"☃\" : { \"☃\" : [ \"☃\", \"☃\" ] }, \"☃\" : true }, \"baz\" : [ \"☃\" ], foo : \"☃\",}", false); // first key needs to be quoted since it contains a space
       
   816 
       
   817 
       
   818   JSONTest::test("[\n]", true);
       
   819 
       
   820   JSONTest::test(
       
   821       "[" "\n"
       
   822       "   {"
       
   823       "         // pattern to match against class+method+signature" "\n"
       
   824       "         // leading and trailing wildcard (*) allowed" "\n"
       
   825       "         match: \"foo.bar.*\"," "\n"
       
   826       " " "\n"
       
   827       "         // override defaults for specified compiler" "\n"
       
   828       "         // we may differentiate between levels too. TBD." "\n"
       
   829       "         c1:  {" "\n"
       
   830       "           //override c1 presets " "\n"
       
   831       "           array_bounds_check_removal: false" "\n"
       
   832       "         }," "\n"
       
   833       "" "\n"
       
   834       "         c2: {" "\n"
       
   835       "           // control inlining of method" "\n"
       
   836       "           // + force inline, - dont inline" "\n"
       
   837       "           inline : [ \"+java.util.*\", \"-com.sun.*\"]," "\n"
       
   838       "         }," "\n"
       
   839       "" "\n"
       
   840       "         // directives outside a specific preset applies to all compilers" "\n"
       
   841       "         inline : [ \"+java.util.*\", \"-com.sun.*\"]," "\n"
       
   842       "         print_assembly: true," "\n"
       
   843       "         verify_oopmaps: true," "\n"
       
   844       "         max_loop_unrolling: 5" "\n"
       
   845       "   }," "\n"
       
   846       "   {" "\n"
       
   847       "         // matching several patterns require an array" "\n"
       
   848       "         match: [\"baz.*\",\"frob*\"]," "\n"
       
   849       "" "\n"
       
   850       "         // only enable c1 for this directive" "\n"
       
   851       "         // all enabled by default. Command disables all not listed" "\n"
       
   852       "         enable: \"c1\"," "\n"
       
   853       "" "\n"
       
   854       "         // applies to all compilers" "\n"
       
   855       "         // + force inline, - dont inline" "\n"
       
   856       "         inline : [ \"+java.util.*\", \"-com.sun.*\"]," "\n"
       
   857       "         print_inlining: true," "\n"
       
   858       "" "\n"
       
   859       "         // force matching compiles to be blocking/syncronous" "\n"
       
   860       "         blocking_compile: true" "\n"
       
   861       "   }," "\n"
       
   862       "]" "\n", true);
       
   863 }
       
   864 
       
   865 void JSONTest::log(uint indent, const char* format, ...) {
       
   866   if (VerboseInternalVMTests) {
       
   867     if (prev != JSON_KEY) {
       
   868       for (uint i = 0; i < indent; i++) {
       
   869         _st->print("  ");
       
   870       }
       
   871     }
       
   872     va_list args;
       
   873     va_start(args, format);
       
   874     _st->vprint(format, args);
       
   875     va_end(args);
       
   876   }
       
   877 }
       
   878 
       
   879 bool JSONTest::callback(JSON_TYPE t, JSON_VAL* v, uint rlevel) {
       
   880   switch (t) {
       
   881   case JSON_OBJECT_BEGIN:
       
   882     log(rlevel, "{\n");
       
   883     prev = JSON_NONE; // Only care about JSON_KEY, to indent correctly
       
   884     return true;
       
   885 
       
   886   case JSON_OBJECT_END:
       
   887     log(rlevel, "},\n");
       
   888     prev = JSON_NONE;
       
   889     return true;
       
   890 
       
   891   case JSON_ARRAY_BEGIN:
       
   892     log(rlevel, "[\n");
       
   893     prev = JSON_NONE;
       
   894     return true;
       
   895 
       
   896   case JSON_ARRAY_END:
       
   897     log(rlevel, "],\n");
       
   898     prev = JSON_NONE;
       
   899     return true;
       
   900 
       
   901   case JSON_KEY:
       
   902     if (VerboseInternalVMTests) {
       
   903       for (uint i = 0; i < rlevel; i++) {
       
   904         _st->print("  ");
       
   905       }
       
   906       _st->print("<key>");
       
   907       for (size_t i = 0; i < v->str.length; i++) {
       
   908         u_char c = v->str.start[i];
       
   909         assert(c != 0, "string overrun");
       
   910         if (c == 0) {
       
   911           return false;
       
   912         }
       
   913         _st->print("%c", c);
       
   914       }
       
   915       _st->print(" : ");
       
   916     }
       
   917     prev = JSON_KEY;
       
   918     return true;
       
   919 
       
   920   case JSON_STRING:
       
   921     if (VerboseInternalVMTests) {
       
   922       if (prev != JSON_KEY) {
       
   923         for (uint i = 0; i < rlevel; i++) {
       
   924           _st->print("  ");
       
   925         }
       
   926       }
       
   927       _st->print("<str>");
       
   928       for (size_t i = 0; i < v->str.length; i++) {
       
   929         u_char c = v->str.start[i];
       
   930         assert(c != 0, "string overrun");
       
   931         if (c == 0) {
       
   932           return false;
       
   933         }
       
   934         _st->print("%c", c);
       
   935       }
       
   936       _st->print(",\n");
       
   937     }
       
   938     prev = JSON_NONE;
       
   939     return true;
       
   940 
       
   941   case JSON_NUMBER_INT:
       
   942     log(rlevel, "<int>%" PRId64 ",\n", v->int_value);
       
   943     prev = JSON_NONE;
       
   944     return true;
       
   945 
       
   946   case JSON_NUMBER_FLOAT:
       
   947     log(rlevel, "<double>%lf,\n", v->double_value);
       
   948     prev = JSON_NONE;
       
   949     return true;
       
   950 
       
   951   case JSON_TRUE:
       
   952     log(rlevel, "<true>,\n");
       
   953     prev = JSON_NONE;
       
   954     return true;
       
   955 
       
   956   case JSON_FALSE:
       
   957     log(rlevel, "<false>,\n");
       
   958     prev = JSON_NONE;
       
   959     return true;
       
   960 
       
   961   case JSON_NULL:
       
   962     log(rlevel, "<null>,\n");
       
   963     prev = JSON_NONE;
       
   964     return true;
       
   965 
       
   966   default:
       
   967     error(INTERNAL_ERROR, "unknown JSON type");
       
   968     return false;
       
   969   }
       
   970 }
       
   971 #endif