├── .gitignore ├── .gitmodules ├── AUTHORS ├── INSTALL.md ├── LICENSE ├── Makefile ├── Makefile.nall ├── README.md ├── SECURITY.md ├── SUBSTANCE.md ├── client ├── README.md └── node-sln-client │ ├── examples │ ├── mime.json │ ├── sln-add-tags │ ├── sln-blog-reimport │ ├── sln-cat │ ├── sln-dump │ ├── sln-export │ ├── sln-extract-metadata │ ├── sln-import │ ├── sln-load │ ├── sln-pipe │ ├── sln-query │ ├── sln-stats │ ├── sln-verify-content │ ├── sln-verify-from-fs │ └── sln-verify-from-list │ ├── sln-client.js │ └── tests │ └── test-meta ├── configure ├── deps ├── cmark │ ├── .editorconfig │ ├── .gitignore │ ├── .travis.yml │ ├── CMakeLists.txt │ ├── COPYING │ ├── FindAsan.cmake │ ├── Makefile │ ├── Makefile.nmake │ ├── README.md │ ├── api_test │ │ ├── CMakeLists.txt │ │ ├── cplusplus.cpp │ │ ├── cplusplus.h │ │ ├── harness.c │ │ ├── harness.h │ │ └── main.c │ ├── appveyor.yml │ ├── bench │ │ ├── statistics.py │ │ └── stats.py │ ├── benchmarks.md │ ├── changelog.txt │ ├── data │ │ └── CaseFolding-3.2.0.txt │ ├── man │ │ ├── CMakeLists.txt │ │ ├── make_man_page.py │ │ ├── man1 │ │ │ └── cmark.1 │ │ └── man3 │ │ │ └── cmark.3 │ ├── nmake.bat │ ├── src │ │ ├── CMakeLists.txt │ │ ├── blocks.c │ │ ├── buffer.c │ │ ├── buffer.h │ │ ├── case_fold_switch.inc │ │ ├── chunk.h │ │ ├── cmark.c │ │ ├── cmark.h │ │ ├── cmark_ctype.c │ │ ├── cmark_ctype.h │ │ ├── cmark_version.h.in │ │ ├── commonmark.c │ │ ├── config.h.in │ │ ├── entities.inc │ │ ├── houdini.h │ │ ├── houdini_href_e.c │ │ ├── houdini_html_e.c │ │ ├── houdini_html_u.c │ │ ├── html.c │ │ ├── inlines.c │ │ ├── inlines.h │ │ ├── iterator.c │ │ ├── iterator.h │ │ ├── latex.c │ │ ├── libcmark.pc.in │ │ ├── main.c │ │ ├── man.c │ │ ├── node.c │ │ ├── node.h │ │ ├── parser.h │ │ ├── references.c │ │ ├── references.h │ │ ├── render.c │ │ ├── render.h │ │ ├── scanners.c │ │ ├── scanners.h │ │ ├── scanners.re │ │ ├── utf8.c │ │ ├── utf8.h │ │ └── xml.c │ ├── test │ │ ├── CMakeLists.txt │ │ ├── afl_dictionary │ │ │ ├── asterisk │ │ │ ├── attr_generic │ │ │ ├── attr_href │ │ │ ├── attr_xml_lang │ │ │ ├── attr_xmlns │ │ │ ├── backslash │ │ │ ├── backtick │ │ │ ├── colon │ │ │ ├── dashes │ │ │ ├── double_quote │ │ │ ├── entity_builtin │ │ │ ├── entity_decimal │ │ │ ├── entity_external │ │ │ ├── entity_hex │ │ │ ├── equals │ │ │ ├── exclamation │ │ │ ├── greater_than │ │ │ ├── hash │ │ │ ├── hyphen │ │ │ ├── indent │ │ │ ├── left_bracket │ │ │ ├── left_paren │ │ │ ├── less_than │ │ │ ├── plus │ │ │ ├── right_bracket │ │ │ ├── right_paren │ │ │ ├── single_quote │ │ │ ├── string_any │ │ │ ├── string_brackets │ │ │ ├── string_cdata │ │ │ ├── string_dashes │ │ │ ├── string_empty_dblquotes │ │ │ ├── string_empty_quotes │ │ │ ├── string_idrefs │ │ │ ├── string_parentheses │ │ │ ├── string_pcdata │ │ │ ├── tag_cdata │ │ │ ├── tag_close │ │ │ ├── tag_doctype │ │ │ ├── tag_element │ │ │ ├── tag_entity │ │ │ ├── tag_notation │ │ │ ├── tag_open │ │ │ ├── tag_open_close │ │ │ ├── tag_open_exclamation │ │ │ ├── tag_open_q │ │ │ ├── tag_sq2_close │ │ │ ├── tag_xml_q │ │ │ └── underscore │ │ ├── afl_test_cases │ │ │ └── test.md │ │ ├── cmark.py │ │ ├── normalize.py │ │ ├── pathological_tests.py │ │ ├── regression.txt │ │ ├── roundtrip_tests.py │ │ ├── smart_punct.txt │ │ ├── spec.txt │ │ └── spec_tests.py │ ├── toolchain-mingw32.cmake │ ├── tools │ │ ├── appveyor-build.bat │ │ ├── make_entities_inc.py │ │ └── mkcasefold.pl │ ├── why-cmark-and-not-x.md │ └── wrappers │ │ ├── wrapper.py │ │ ├── wrapper.rb │ │ └── wrapper.rkt ├── content-disposition │ ├── LICENSE │ ├── content-disposition.c │ └── content-disposition.h ├── crypt_blowfish │ ├── LINKS │ ├── Makefile │ ├── PERFORMANCE │ ├── README │ ├── crypt.3 │ ├── crypt.h │ ├── crypt_blowfish.c │ ├── crypt_blowfish.h │ ├── crypt_gensalt.c │ ├── crypt_gensalt.h │ ├── glibc-2.1.3-crypt.diff │ ├── glibc-2.14-crypt.diff │ ├── glibc-2.3.6-crypt.diff │ ├── ow-crypt.h │ ├── wrapper.c │ └── x86.S ├── fts3 │ ├── fts3Int.h │ ├── fts3_porter.c │ ├── fts3_tokenizer.h │ └── sqlite3.h ├── memorymapping │ ├── README.md │ ├── deps.json │ └── src │ │ ├── NimbusMemoryMapping.h │ │ ├── fmemopen.c │ │ └── fmemopen.h ├── smhasher │ ├── AvalancheTest.cpp │ ├── AvalancheTest.h │ ├── Bitslice.cpp │ ├── Bitvec.cpp │ ├── Bitvec.h │ ├── CMakeLists.txt │ ├── City.cpp │ ├── City.h │ ├── CityTest.cpp │ ├── DifferentialTest.cpp │ ├── DifferentialTest.h │ ├── Hashes.cpp │ ├── Hashes.h │ ├── KeysetTest.cpp │ ├── KeysetTest.h │ ├── MurmurHash1.cpp │ ├── MurmurHash1.h │ ├── MurmurHash2.cpp │ ├── MurmurHash2.h │ ├── MurmurHash3.cpp │ ├── MurmurHash3.h │ ├── PMurHash.c │ ├── PMurHash.h │ ├── Platform.cpp │ ├── Platform.h │ ├── Random.cpp │ ├── Random.h │ ├── SpeedTest.cpp │ ├── SpeedTest.h │ ├── Spooky.cpp │ ├── Spooky.h │ ├── SpookyTest.cpp │ ├── Stats.cpp │ ├── Stats.h │ ├── SuperFastHash.cpp │ ├── Types.cpp │ ├── Types.h │ ├── crc.cpp │ ├── lookup3.cpp │ ├── main.cpp │ ├── md5.cpp │ ├── pstdint.h │ ├── sha1.cpp │ └── sha1.h └── yajl │ ├── .gitignore │ ├── BUILDING │ ├── BUILDING.win32 │ ├── CMakeLists.txt │ ├── COPYING │ ├── ChangeLog │ ├── README │ ├── TODO │ ├── YAJLDoc.cmake │ ├── configure │ ├── example │ ├── CMakeLists.txt │ ├── README.md │ ├── parse_config.c │ └── sample.config │ ├── perf │ ├── CMakeLists.txt │ ├── documents.c │ ├── documents.h │ └── perftest.c │ ├── reformatter │ ├── CMakeLists.txt │ └── json_reformat.c │ ├── src │ ├── CMakeLists.txt │ ├── YAJL.dxy │ ├── api │ │ ├── yajl_common.h │ │ ├── yajl_gen.h │ │ ├── yajl_parse.h │ │ ├── yajl_tree.h │ │ └── yajl_version.h.cmake │ ├── yajl │ ├── yajl.c │ ├── yajl.pc.cmake │ ├── yajl_alloc.c │ ├── yajl_alloc.h │ ├── yajl_buf.c │ ├── yajl_buf.h │ ├── yajl_bytestack.h │ ├── yajl_encode.c │ ├── yajl_encode.h │ ├── yajl_gen.c │ ├── yajl_lex.c │ ├── yajl_lex.h │ ├── yajl_parser.c │ ├── yajl_parser.h │ ├── yajl_tree.c │ └── yajl_version.c │ ├── test │ ├── CMakeLists.txt │ ├── api │ │ ├── CMakeLists.txt │ │ ├── gen-extra-close.c │ │ └── run_tests.sh │ └── parsing │ │ ├── CMakeLists.txt │ │ ├── cases │ │ ├── ac_difficult_json_c_test_case_with_comments.json │ │ ├── ac_difficult_json_c_test_case_with_comments.json.gold │ │ ├── ac_simple_with_comments.json │ │ ├── ac_simple_with_comments.json.gold │ │ ├── ag_false_then_garbage.json │ │ ├── ag_false_then_garbage.json.gold │ │ ├── ag_null_then_garbage.json │ │ ├── ag_null_then_garbage.json.gold │ │ ├── ag_true_then_garbage.json │ │ ├── ag_true_then_garbage.json.gold │ │ ├── am_eof.json │ │ ├── am_eof.json.gold │ │ ├── am_integers.json │ │ ├── am_integers.json.gold │ │ ├── am_multiple.json │ │ ├── am_multiple.json.gold │ │ ├── am_stuff.json │ │ ├── am_stuff.json.gold │ │ ├── ap_array_open.json │ │ ├── ap_array_open.json.gold │ │ ├── ap_eof_str.json │ │ ├── ap_eof_str.json.gold │ │ ├── ap_map_open.json │ │ ├── ap_map_open.json.gold │ │ ├── ap_partial_ok.json │ │ ├── ap_partial_ok.json.gold │ │ ├── array.json │ │ ├── array.json.gold │ │ ├── array_close.json │ │ ├── array_close.json.gold │ │ ├── bignums.json │ │ ├── bignums.json.gold │ │ ├── bogus_char.json │ │ ├── bogus_char.json.gold │ │ ├── codepoints_from_unicode_org.json │ │ ├── codepoints_from_unicode_org.json.gold │ │ ├── deep_arrays.json │ │ ├── deep_arrays.json.gold │ │ ├── difficult_json_c_test_case.json │ │ ├── difficult_json_c_test_case.json.gold │ │ ├── doubles.json │ │ ├── doubles.json.gold │ │ ├── doubles_in_array.json │ │ ├── doubles_in_array.json.gold │ │ ├── empty_array.json │ │ ├── empty_array.json.gold │ │ ├── empty_string.json │ │ ├── empty_string.json.gold │ │ ├── escaped_bulgarian.json │ │ ├── escaped_bulgarian.json.gold │ │ ├── escaped_foobar.json │ │ ├── escaped_foobar.json.gold │ │ ├── false.json │ │ ├── false.json.gold │ │ ├── fg_false_then_garbage.json │ │ ├── fg_false_then_garbage.json.gold │ │ ├── fg_issue_7.json │ │ ├── fg_issue_7.json.gold │ │ ├── fg_null_then_garbage.json │ │ ├── fg_null_then_garbage.json.gold │ │ ├── fg_true_then_garbage.json │ │ ├── fg_true_then_garbage.json.gold │ │ ├── four_byte_utf8.json │ │ ├── four_byte_utf8.json.gold │ │ ├── high_overflow.json │ │ ├── high_overflow.json.gold │ │ ├── integers.json │ │ ├── integers.json.gold │ │ ├── invalid_utf8.json │ │ ├── invalid_utf8.json.gold │ │ ├── isolated_surrogate_marker.json │ │ ├── isolated_surrogate_marker.json.gold │ │ ├── leading_zero_in_number.json │ │ ├── leading_zero_in_number.json.gold │ │ ├── lonely_minus_sign.json │ │ ├── lonely_minus_sign.json.gold │ │ ├── lonely_number.json │ │ ├── lonely_number.json.gold │ │ ├── low_overflow.json │ │ ├── low_overflow.json.gold │ │ ├── map_close.json │ │ ├── map_close.json.gold │ │ ├── missing_integer_after_decimal_point.json │ │ ├── missing_integer_after_decimal_point.json.gold │ │ ├── missing_integer_after_exponent.json │ │ ├── missing_integer_after_exponent.json.gold │ │ ├── multiple.json │ │ ├── multiple.json.gold │ │ ├── non_utf8_char_in_string.json │ │ ├── non_utf8_char_in_string.json.gold │ │ ├── np_partial_bad.json │ │ ├── np_partial_bad.json.gold │ │ ├── null.json │ │ ├── null.json.gold │ │ ├── nulls_and_bools.json │ │ ├── nulls_and_bools.json.gold │ │ ├── simple.json │ │ ├── simple.json.gold │ │ ├── simple_with_comments.json │ │ ├── simple_with_comments.json.gold │ │ ├── string_invalid_escape.json │ │ ├── string_invalid_escape.json.gold │ │ ├── string_invalid_hex_char.json │ │ ├── string_invalid_hex_char.json.gold │ │ ├── string_with_escapes.json │ │ ├── string_with_escapes.json.gold │ │ ├── string_with_invalid_newline.json │ │ ├── string_with_invalid_newline.json.gold │ │ ├── three_byte_utf8.json │ │ ├── three_byte_utf8.json.gold │ │ ├── true.json │ │ ├── true.json.gold │ │ ├── unescaped_bulgarian.json │ │ ├── unescaped_bulgarian.json.gold │ │ ├── zerobyte.json │ │ └── zerobyte.json.gold │ │ ├── run_tests.sh │ │ └── yajl_test.c │ └── verify │ ├── CMakeLists.txt │ └── json_verify.c ├── res ├── async_sqlite.c ├── blog │ ├── static │ │ ├── LICENSE │ │ ├── commonmark.min.js │ │ ├── commonmark.min.js.gz │ │ ├── favicon.ico │ │ ├── file.png │ │ ├── hash-handler.html │ │ ├── index.css │ │ └── markdown.js │ └── template │ │ ├── compose.html │ │ ├── empty.html │ │ ├── entry-end.html │ │ ├── entry-start.html │ │ ├── footer.html │ │ ├── header.html │ │ ├── login.html │ │ ├── noresults.html │ │ ├── notfound.html │ │ ├── preview.html │ │ ├── rss │ │ ├── head.xml │ │ ├── item-end.xml │ │ ├── item-start.xml │ │ └── tail.xml │ │ └── upload.html ├── experiments │ ├── 2013-04-22 EarthFS Pull Design.graffle │ ├── 2013-06-07 EFS Auth.js │ ├── 2013-06-15 EFS submission.js │ ├── 2013-07-01 EarthFS Redesign.js │ ├── 2013-08-27 EarthFS Draft.odt │ ├── 2013-08-27 EarthFS design.txt │ ├── 2013-09-12 EarthFS Draft 2.odt │ ├── 2013-09-18-test-fibers.js │ ├── 2013-09-20-efs-queries.sql │ ├── 2013-09-20-node-fibers-error-test-case.js │ ├── 2013-09-22-efs-plugin-api.js │ ├── 2013-09-29-temp.sql │ ├── 2013-10-14-efs-query.js │ ├── 2013-12-07-earthfs-paper-snippets-old.txt │ ├── 2014-01-22-earthfs-internal-file.txt │ ├── 2014-02-04-link-tracking.txt │ ├── 2014-02-05-link-tracking-2.txt │ ├── 2014-05-19-efs-hash.c │ ├── 2014-05-22-easy-http-parser.c │ ├── 2014-05-22-efs-server.c │ ├── 2014-05-23-efs-rest-api.c │ ├── 2014-05-24-efs-http.c │ ├── 2014-05-26-efs-api.c │ ├── 2014-05-27-efs-query.c │ ├── 2014-06-02-querystring.c │ ├── 2014-06-03-efs-db-test.db │ ├── 2014-06-04-dstr.c │ ├── 2014-06-05-efs-schema.sql │ ├── 2014-06-07-sqlite-threadpool.c │ ├── 2014-06-08-sqlite-async.c │ ├── 2014-06-08-sqlite-libuv.c │ ├── 2014-06-10-efs-indexer.c │ ├── 2014-06-10-efs-temp-tables.c │ ├── 2014-06-10-efs-uri-list-parser.c │ ├── 2014-06-10-hypertext-parser.c │ ├── 2014-06-14-peg.c │ ├── 2014-06-15-efs-lineparser.c │ ├── 2014-06-15-headerlist.c │ ├── 2014-06-15-headers.c │ ├── 2014-06-16-headers.c │ ├── 2014-06-16-multipart.c │ ├── 2014-06-22-blog-server.c │ ├── 2014-06-23-htmlenc.c │ ├── 2014-06-23-uv-printf.c │ ├── 2014-06-24-event-attributes.js │ ├── 2014-06-24-http-io.c │ ├── 2014-06-26-meta-file.c │ ├── 2014-06-26-template.c │ ├── 2014-06-29-headers.c │ ├── 2014-06-29-session-cache.c │ ├── 2014-06-30-rwlock.c │ ├── 2014-07-01-connection-pool.c │ ├── 2014-07-06-pull.c │ ├── 2014-07-13-filters.c │ ├── 2014-07-17-new-mutex.c │ ├── 2014-07-19-test-data.sql │ ├── 2014-07-20-query-parser.txt │ ├── 2014-07-21-query-parser.c │ ├── 2014-07-26-async-sqlite-pool.c │ ├── 2014-07-27-query-cache.c │ ├── 2014-07-28-efs-profile.txt │ ├── 2014-07-29-juan-reply.txt │ ├── 2014-08-02-filter.c │ ├── 2014-08-05-filter-system.txt │ ├── 2014-08-07-async-worker.c │ ├── 2014-08-16-query-tests.sql │ ├── 2014-08-18-efs-dump.c │ ├── 2014-08-18-efs-schema-old.sql │ ├── 2014-08-27-efspush.c │ ├── 2014-08-29-db-schema.c │ ├── 2014-08-29-filters.sql │ ├── 2014-08-31-efs-filter-refactor.c │ ├── 2014-09-05-efs-submission-wait.c │ ├── 2014-09-06-query.c │ ├── 2014-09-07-worker-pool.c │ ├── 2014-09-08-EFSMutableTagFilter.m │ ├── 2014-09-08-meta-file-filter.m │ ├── 2014-09-18-pmap.c │ ├── 2014-09-19-stress.js │ ├── 2014-09-22-lsmdb.c │ ├── 2014-09-23-lsmdb.c │ ├── 2014-09-23-mdb-email.txt │ ├── 2014-09-24-lsmdb.c │ ├── 2014-09-24-lsmdb2.c │ ├── 2014-09-24-mdb-feature-requests.txt │ ├── 2014-09-29-db-api-compare.c │ ├── 2014-09-30-db-wrapper.c │ ├── 2014-10-01-lsmdb.c │ ├── 2014-10-10-lsmdb.c │ ├── 2014-10-12-swap.c │ ├── 2014-10-18-cursor-pfx.c │ ├── 2014-10-21-db.c │ ├── 2014-10-22-filter-rewrite.c │ ├── 2014-10-23-db-generic.c │ ├── 2014-10-27-db-leveldb.c │ ├── 2014-10-28-sorted-map.c │ ├── 2014-11-01-ldb-cursor.c │ ├── 2014-11-02-databases.txt │ ├── 2014-11-16-db-sophia.c │ ├── 2014-11-18-efs-fts.c │ ├── 2015-01-01-stronglink-interface.h │ ├── 2015-01-09-push.c │ ├── 2015-01-10-sync.c │ ├── 2015-01-20-async-read.c │ ├── 2015-02-01-http-parser.c │ ├── 2015-02-10-select.c │ ├── 2015-02-10-sync.c │ ├── 2015-02-19-async-cancelable.c │ ├── 2015-02-19-async-read-new.c │ ├── 2015-02-22-hash-table.c │ ├── 2015-02-22-import-c2.js │ ├── 2015-02-23-session-cookie.c │ ├── 2015-02-27-cookie.c │ ├── 2015-02-27-headers.c │ ├── 2015-02-28-errors.c │ ├── 2015-03-02-login.html │ ├── 2015-03-02-markdown.c │ ├── 2015-03-06-fsmash-style-login.html │ ├── 2015-03-07-cmark.c │ ├── 2015-03-08-multipart.c │ ├── 2015-03-09-meta-file-parser.c │ ├── 2015-03-10-config.c │ ├── 2015-03-13-db.c │ ├── 2015-03-14-schema.c │ ├── 2015-03-18-filters.c │ ├── 2015-03-21-filters.c │ ├── 2015-03-21-rtree.c │ ├── 2015-03-23-sync.c │ ├── 2015-03-25-asprintf.c │ ├── 2015-03-27-dirname.c │ ├── 2015-03-29-cookie-cache.c │ ├── 2015-04-07-plaintext.c │ ├── 2015-04-19-batch-meta.js │ ├── 2015-04-20-query-opts.c │ ├── 2015-04-25-client-api.js │ ├── 2015-04-25-tag-all.js │ ├── 2015-04-26-non-meta-filter.m │ ├── 2015-04-27-uri-filter.m │ ├── 2015-05-02-hash-anatomy.xcf │ ├── 2015-05-08-parse-content-disposition.c │ ├── 2015-05-14-touch-buffer.c │ ├── 2015-05-16-default-port.txt │ ├── 2015-05-31-file-cache.c │ ├── 2015-06-07-file-cache.c │ ├── 2015-06-21-filter-stream-2.c │ ├── 2015-06-21-filter-stream.c │ ├── 2015-06-23-sync.c │ ├── 2015-07-20-links-to-filter.m │ ├── 2015-07-20-sendfile.c │ ├── 2015-07-27-test-server.js │ ├── 2015-08-05-libuv-runloop-death.c │ ├── 2015-08-15-test.c │ ├── 2015-08-16-tls.c │ ├── 2015-08-20-node-keepalive-test.js │ ├── 2015-08-21-buffered-io.c │ ├── 2015-08-22-io-architecture.gif │ └── 2015-08-22-io-architecture.odg └── favicon.xcf └── src ├── SLNDB.h ├── SLNHasher.c ├── SLNPull.c ├── SLNRepo.c ├── SLNServer.c ├── SLNSession.c ├── SLNSessionCache.c ├── SLNSubmission.c ├── SLNSubmissionMeta.c ├── SLNSync.c ├── StrongLink.h ├── blog ├── Blog.c ├── Blog.h ├── BlogConvert.c ├── RSSServer.c ├── RSSServer.h ├── Template.c ├── Template.h ├── converter.h ├── main.c ├── markdown.c └── plaintext.c ├── common.h ├── filter ├── SLNCollectionFilter.m ├── SLNDirectFilter.m ├── SLNFilter.h ├── SLNFilter.m ├── SLNFilterExt.c ├── SLNIndirectFilter.m ├── SLNJSONFilterParser.c ├── SLNLinksToFilter.m ├── SLNMetaFileFilter.m ├── SLNNegationFilter.m └── SLNUserFilterParser.c └── util ├── fts.c ├── fts.h ├── libco_coro.c ├── pass.c ├── pass.h ├── raiserlimit.h ├── strext.c └── strext.h /.gitignore: -------------------------------------------------------------------------------- 1 | build/ 2 | perf.data 3 | perf.data.old 4 | deps/uv/uv.xcodeproj 5 | *~ 6 | .DS_Store 7 | 8 | # Exclude these from GitHub language statistics 9 | # https://help.github.com/articles/my-repository-is-marked-as-the-wrong-language/ 10 | # https://github.com/github/linguist#readme 11 | /res/experiments linguist-documentation 12 | res/async_sqlite.c linguist-documentation 13 | 14 | /deps/yajl/test/parsing/cases/am_stuff.json.out 15 | /deps/yajl/test/parsing/cases/am_stuff.json.test 16 | 17 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "deps/libasync"] 2 | path = deps/libasync 3 | url = ../libasync/ 4 | [submodule "deps/libkvstore"] 5 | path = deps/libkvstore 6 | url = ../libkvstore 7 | -------------------------------------------------------------------------------- /AUTHORS: -------------------------------------------------------------------------------- 1 | Ben Trask 2 | 3 | 4 | Your name here! 5 | 6 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Dependencies are used under their own licenses. See each dependency 2 | directory in ./deps. 3 | 4 | The generic file icon is used under the LGPL. See 5 | ./res/blog/static/LICENSE. 6 | 7 | --- 8 | 9 | Copyright (c) 2014-2015 Ben Trask 10 | 11 | Permission is hereby granted, free of charge, to any person obtaining a 12 | copy of this software and associated documentation files (the "Software"), 13 | to deal in the Software without restriction, including without limitation 14 | the rights to use, copy, modify, merge, publish, distribute, sublicense, 15 | and/or sell copies of the Software, and to permit persons to whom the 16 | Software is furnished to do so, subject to the following conditions: 17 | 18 | The above copyright notice and this permission notice shall be included 19 | in all copies or substantial portions of the Software. 20 | 21 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 22 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 23 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 24 | THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR 25 | OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, 26 | ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR 27 | OTHER DEALINGS IN THE SOFTWARE. 28 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-add-tags: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2014-2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var sln = require("../sln-client"); 6 | 7 | if(process.argv.length <= 4) { 8 | console.error("Usage: sln-add-tags repo [tag ...] query"); 9 | process.exit(1); 10 | } 11 | var repo = sln.repoForName(process.argv[2]); 12 | var tags = process.argv.slice(3, -1); 13 | var query = process.argv.slice(-1)[0]; 14 | 15 | function array2obj(array) { 16 | var obj = {}; 17 | for(var i = 0; i < array.length; i++) { 18 | obj[array[i]] = {}; 19 | } 20 | return obj; 21 | } 22 | 23 | var meta = { 24 | "tag": array2obj(tags), 25 | }; 26 | 27 | var stream = repo.createQueryStream(query, { wait: false }); 28 | stream.on("data", function(URI) { 29 | stream.pause(); 30 | repo.submitMeta(URI, meta, {}, function(err, obj) { 31 | if(err) throw err; 32 | stream.resume(); 33 | console.log(URI); 34 | }); 35 | }); 36 | 37 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-blog-reimport: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2014-2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var http = require("http"); 6 | var crypto = require("crypto"); 7 | var urimodule = require("url"); 8 | 9 | var sln = require("../sln-client"); 10 | 11 | if(process.argv.length <= 3) { 12 | console.error("Usage: sln-blog-reimport src dst"); 13 | process.exit(1); 14 | } 15 | var src = sln.repoForName(process.argv[2]); 16 | var dst = sln.repoForName(process.argv[3]); 17 | 18 | var boundary = "----------"+crypto.randomBytes(16).toString("hex"); 19 | 20 | var stream = src.createQueryStream("", { wait: false }); 21 | stream.on("data", function(URI) { 22 | stream.pause(); 23 | console.log(URI); 24 | var req1 = src.createFileRequest(URI, {}); 25 | req1.on("response", function(res1) { 26 | if(200 !== res1.statusCode) throw new Error("HTTP status "+res1.statusCode); 27 | var req2 = http.request({ 28 | method: "POST", 29 | hostname: dst.hostname, 30 | port: dst.port, 31 | path: dst.path+"/post", 32 | headers: { 33 | "Cookie": "s="+dst.session, 34 | "Content-Type": "multipart/form-data; boundary="+boundary, 35 | }, 36 | }); 37 | req2.write("--"+boundary+"\r\n", "utf8"); 38 | req2.write("Content-Disposition: form-data; name=\"file\""+"\r\n", "utf8"); 39 | req2.write("Content-Type: "+res1.headers["content-type"]+"\r\n", "utf8"); 40 | req2.write("\r\n", "utf8"); 41 | res1.pipe(req2, { end: false }); 42 | res1.on("end", function() { 43 | req2.write("\r\n", "utf8"); 44 | req2.write("--"+boundary+"--", "utf8"); 45 | req2.end(); 46 | }); 47 | req2.on("response", function(res2) { 48 | if(303 !== res2.statusCode) throw new Error("HTTP status "+res2.statusCode); 49 | // TODO: We can't tell between success and auth redirects... 50 | res2.resume(); // drain 51 | stream.resume(); 52 | }); 53 | }); 54 | }); 55 | 56 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-cat: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var sln = require("../sln-client"); 6 | 7 | if(process.argv.length <= 3) { 8 | console.error("Usage: sln-cat repo link"); 9 | process.exit(1); 10 | } 11 | var repo = sln.repoForName(process.argv[2]); 12 | var link = process.argv[3]; 13 | 14 | var req = repo.createFileRequest(link, {}); 15 | req.on("response", function(res) { 16 | if(200 !== res.statusCode) throw new Error("Response error "+res.statusCode); 17 | res.pipe(process.stdout); 18 | }); 19 | 20 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-query: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2014-2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var sln = require("../sln-client"); 6 | 7 | if(process.argv.length <= 2) { 8 | console.error("Usage: sln-query repo [query]"); 9 | process.exit(1); 10 | } 11 | var repo = sln.repoForName(process.argv[2]); 12 | var query = process.argv[3] || ""; 13 | 14 | var stream = repo.createQueryStream(query, {}); 15 | stream.on("data", function(URI) { 16 | console.log(URI); 17 | }); 18 | 19 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-verify-content: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2014-2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var crypto = require("crypto"); 6 | 7 | var sln = require("../sln-client"); 8 | 9 | if(process.argv.length <= 2) { 10 | console.error("Usage: sln-verify-content repo [query]"); 11 | process.exit(1); 12 | } 13 | var repo = sln.repoForName(process.argv[2]); 14 | var query = process.argv[3] || ""; 15 | 16 | var stats = { 17 | bad: 0, 18 | total: 0, 19 | }; 20 | 21 | var stream = repo.createQueryStream(query, { wait: false }); 22 | function report(URI, msg) { 23 | stats.bad++; 24 | console.log(URI); 25 | console.log("\t"+msg); 26 | stream.resume(); 27 | } 28 | 29 | stream.on("data", function(URI) { 30 | stream.pause(); 31 | stats.total++; 32 | 33 | var req = repo.createFileRequest(URI, {}); 34 | req.on("response", function(res) { 35 | if(200 != res.statusCode) { 36 | return report(URI, "Error: "+res.statusCode+" response"); 37 | } 38 | 39 | var uriobj = sln.parseURI(URI); 40 | var actuallen = 0; 41 | var hasher = crypto.createHash(uriobj.algo); 42 | res.on("data", function(chunk) { 43 | actuallen += chunk.length; 44 | hasher.write(chunk); 45 | }); 46 | res.on("end", function() { 47 | var expectedhash = uriobj.hash; 48 | hasher.end(); 49 | var actualhash = hasher.read().toString("hex"); 50 | if(actualhash !== expectedhash) { 51 | return report(URI, "Error: bad hash "+actualhash); 52 | } 53 | 54 | // Not sure this check is worthwhile. 55 | var expectedlen = +res.headers["content-length"]; 56 | if(actuallen !== expectedlen) { 57 | return report(URI, "Error: expected "+expectedlen+" bytes but got "+actuallen+" bytes"); 58 | } 59 | 60 | stream.resume(); 61 | }); 62 | }); 63 | }); 64 | stream.on("end", function() { 65 | console.log(""); 66 | console.log(stats.bad+" errors out of "+stats.total+" total files"); 67 | }); 68 | 69 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-verify-from-fs: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var crypto = require("crypto"); 6 | var fs = require("fs"); 7 | var pathmodule = require("path"); 8 | 9 | var sln = require("../sln-client"); 10 | 11 | if(process.argv.length <= 4) { 12 | console.error("Usage: sln-verify-from-fs repo path algo"); 13 | process.exit(1); 14 | } 15 | var repo = sln.repoForName(process.argv[2]); 16 | var path = process.argv[3]; 17 | var algo = process.argv[4]; 18 | 19 | // This script is mainly useful for testing against very old versions of 20 | // StrongLink (even from before it was called StrongLink). 21 | 22 | // This tool just uses the directory tree at `path` as a list of hashes 23 | // under the `algo` algorithm. The old files are assumed to match their 24 | // hashes. The new files can be verified with the sln-verify-content tool. 25 | 26 | fs.readdir(path, function(err, dirs) { 27 | if(err) throw err; 28 | (function nexti(i) { 29 | if(i >= dirs.length) return; 30 | var dir = pathmodule.join(path, dirs[i]); 31 | fs.readdir(dir, function(err, files) { 32 | if(err) throw err; 33 | (function nextj(j) { 34 | if(j >= files.length) return nexti(i+1); 35 | var file = pathmodule.join(dir, files[j]); 36 | console.log(file); 37 | repo.getFile("hash://"+algo+"/"+files[j], {method: "HEAD"}, function(err, obj) { 38 | if(err) throw err; 39 | nextj(j+1); 40 | }); 41 | })(0); 42 | }); 43 | })(0); 44 | }); 45 | 46 | -------------------------------------------------------------------------------- /client/node-sln-client/examples/sln-verify-from-list: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var crypto = require("crypto"); 6 | var fs = require("fs"); 7 | 8 | var sln = require("../sln-client"); 9 | 10 | if(process.argv.length <= 3) { 11 | console.error("Usage: sln-verify-from-list repo path"); 12 | process.exit(1); 13 | } 14 | var repo = sln.repoForName(process.argv[2]); 15 | var path = process.argv[3]; 16 | 17 | // Note: file order isn't verified here because it isn't 18 | // guaranteed in all cases. 19 | 20 | var list = fs.createReadStream(path, { encoding: "utf8" }); 21 | var stream = new sln.URIListStream(); 22 | list.pipe(stream); 23 | 24 | stream.on("data", function(URI) { 25 | stream.pause(); 26 | console.log(URI); 27 | repo.getFile(URI, { method: "HEAD" }, function(err, obj) { 28 | if(err) throw err; 29 | stream.resume(); 30 | }); 31 | }); 32 | 33 | -------------------------------------------------------------------------------- /client/node-sln-client/tests/test-meta: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | // Copyright 2015 Ben Trask 3 | // MIT licensed (see LICENSE for details) 4 | 5 | var crypto = require("crypto"); 6 | var sln = require("../sln-client"); 7 | 8 | if(process.argv.length <= 2) { 9 | console.error("Usage: test-meta repo"); 10 | process.exit(1); 11 | } 12 | var repo = sln.repoForName(process.argv[2]); 13 | 14 | // A meta-file cannot target another meta-file. 15 | var metafiles = repo.createMetafilesStream({ wait: false, count: 1 }); 16 | metafiles.on("data", function(info) { 17 | var meta = { 18 | "test-data": crypto.pseudoRandomBytes(8).toString("hex"), 19 | }; 20 | repo.submitMeta(info.uri, meta, {}, function(err, added) { 21 | if(!err) throw new Error("Meta-file added with invalid target"); 22 | console.log("Success"); 23 | }); 24 | }); 25 | 26 | -------------------------------------------------------------------------------- /configure: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | set -e 3 | 4 | (cd ./deps/libasync && ./configure) 5 | (cd ./deps/libkvstore && ./configure) 6 | (cd ./deps/yajl && ./configure) 7 | -------------------------------------------------------------------------------- /deps/cmark/.editorconfig: -------------------------------------------------------------------------------- 1 | # editorconfig.org 2 | 3 | root = true 4 | 5 | [*] 6 | end_of_line = lf 7 | charset = utf-8 8 | insert_final_newline = true 9 | 10 | [*.{c,h}] 11 | trim_trailing_whitespace = true 12 | indent_style = space 13 | indent_size = 2 14 | 15 | [Makefile] 16 | trim_trailing_whitespace = true 17 | indent_style = tab 18 | indent_size = 8 19 | -------------------------------------------------------------------------------- /deps/cmark/.gitignore: -------------------------------------------------------------------------------- 1 | # Object files 2 | *.o 3 | *.ko 4 | *.obj 5 | *.elf 6 | 7 | # Libraries 8 | *.lib 9 | *.a 10 | 11 | # Shared objects (inc. Windows DLLs) 12 | *.dll 13 | *.so 14 | *.so.* 15 | *.dylib 16 | 17 | # Executables 18 | *.exe 19 | *.out 20 | *.app 21 | *.i*86 22 | *.x86_64 23 | *.hex 24 | *.pyc 25 | 26 | *~ 27 | *.bak 28 | *.diff 29 | *# 30 | *.zip 31 | bstrlib.txt 32 | build 33 | cmark.dSYM/* 34 | cmark 35 | -------------------------------------------------------------------------------- /deps/cmark/.travis.yml: -------------------------------------------------------------------------------- 1 | # Ensures that sudo is disabled, so that containerized builds are allowed 2 | sudo: false 3 | 4 | os: 5 | - linux 6 | - osx 7 | language: c 8 | compiler: 9 | - clang 10 | - gcc 11 | addons: 12 | apt: 13 | # we need a more recent cmake than travis/linux provides (at least 2.8.9): 14 | sources: 15 | - kubuntu-backports 16 | packages: 17 | - cmake 18 | - python3 19 | - valgrind 20 | before_install: 21 | - | 22 | if [ ${TRAVIS_OS_NAME:-'linux'} = 'osx' ] 23 | then 24 | echo "Building without python3, to make sure that works." 25 | fi 26 | script: 27 | - make 28 | - make test 29 | - | 30 | if [ ${TRAVIS_OS_NAME:-'linux'} = 'linux' ] 31 | then 32 | make leakcheck 33 | fi 34 | -------------------------------------------------------------------------------- /deps/cmark/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 2.8.9) 2 | project(cmark) 3 | include("FindAsan.cmake") 4 | 5 | if("${CMAKE_SOURCE_DIR}" STREQUAL "${CMAKE_BINARY_DIR}") 6 | message(FATAL_ERROR "Do not build in-source.\nPlease remove CMakeCache.txt and the CMakeFiles/ directory.\nThen: mkdir build ; cd build ; cmake .. ; make") 7 | endif() 8 | 9 | set(PROJECT_NAME "cmark") 10 | 11 | set(PROJECT_VERSION_MAJOR 0) 12 | set(PROJECT_VERSION_MINOR 25) 13 | set(PROJECT_VERSION_PATCH 2) 14 | set(PROJECT_VERSION ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}.${PROJECT_VERSION_PATCH} ) 15 | 16 | option(CMARK_TESTS "Build cmark tests and enable testing" ON) 17 | 18 | add_subdirectory(src) 19 | if(CMARK_TESTS) 20 | add_subdirectory(api_test) 21 | endif() 22 | add_subdirectory(man) 23 | if(CMARK_TESTS) 24 | enable_testing() 25 | add_subdirectory(test testdir) 26 | endif() 27 | 28 | if(NOT CMAKE_BUILD_TYPE) 29 | set(CMAKE_BUILD_TYPE "Release" CACHE STRING 30 | "Choose the type of build, options are: Debug Profile Release Asan Ubsan." FORCE) 31 | endif(NOT CMAKE_BUILD_TYPE) 32 | -------------------------------------------------------------------------------- /deps/cmark/Makefile.nmake: -------------------------------------------------------------------------------- 1 | SRCDIR=src 2 | DATADIR=data 3 | BUILDDIR=build 4 | INSTALLDIR=windows 5 | SPEC=test/spec.txt 6 | PROG=$(BUILDDIR)\src\cmark.exe 7 | GENERATOR=NMake Makefiles 8 | 9 | all: $(BUILDDIR)/CMakeFiles 10 | @cd $(BUILDDIR) && $(MAKE) /nologo && cd .. 11 | 12 | $(BUILDDIR)/CMakeFiles: 13 | @-mkdir $(BUILDDIR) 2> nul 14 | cd $(BUILDDIR) && \ 15 | cmake \ 16 | -G "$(GENERATOR)" \ 17 | -D CMAKE_BUILD_TYPE=$(BUILD_TYPE) \ 18 | -D CMAKE_INSTALL_PREFIX=$(INSTALLDIR) \ 19 | .. && \ 20 | cd .. 21 | 22 | install: all 23 | @cd $(BUILDDIR) && $(MAKE) /nologo install && cd .. 24 | 25 | clean: 26 | -rmdir /s /q $(BUILDDIR) $(MINGW_INSTALLDIR) 2> nul 27 | 28 | $(SRCDIR)\case_fold_switch.inc: $(DATADIR)\CaseFolding-3.2.0.txt 29 | perl mkcasefold.pl < $? > $@ 30 | 31 | test: $(SPEC) all 32 | @cd $(BUILDDIR) && $(MAKE) /nologo test ARGS="-V" && cd .. 33 | 34 | distclean: clean 35 | del /q src\scanners.c 2> nul 36 | del /q spec.md spec.html 2> nul 37 | -------------------------------------------------------------------------------- /deps/cmark/api_test/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | add_executable(api_test 2 | cplusplus.cpp 3 | harness.c 4 | harness.h 5 | main.c 6 | ) 7 | include_directories( 8 | ${PROJECT_SOURCE_DIR}/src 9 | ${PROJECT_BINARY_DIR}/src 10 | ) 11 | target_link_libraries(api_test libcmark) 12 | 13 | # Compiler flags 14 | if(MSVC) 15 | # Force to always compile with W4 16 | if(CMAKE_CXX_FLAGS MATCHES "/W[0-4]") 17 | string(REGEX REPLACE "/W[0-4]" "/W4" CMAKE_C_FLAGS "${CMAKE_C_FLAGS}") 18 | else() 19 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /W4") 20 | endif() 21 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4706 /D_CRT_SECURE_NO_WARNINGS") 22 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /TP") 23 | elseif(CMAKE_COMPILER_IS_GNUCC OR "${CMAKE_C_COMPILER_ID}" STREQUAL "Clang") 24 | set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wextra -std=c99 -pedantic") 25 | endif() 26 | -------------------------------------------------------------------------------- /deps/cmark/api_test/cplusplus.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include "cmark.h" 4 | #include "cplusplus.h" 5 | #include "harness.h" 6 | 7 | void 8 | test_cplusplus(test_batch_runner *runner) 9 | { 10 | static const char md[] = "paragraph\n"; 11 | char *html = cmark_markdown_to_html(md, sizeof(md) - 1, CMARK_OPT_DEFAULT); 12 | STR_EQ(runner, html, "

paragraph

\n", "libcmark works with C++"); 13 | free(html); 14 | } 15 | 16 | -------------------------------------------------------------------------------- /deps/cmark/api_test/cplusplus.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_API_TEST_CPLUSPLUS_H 2 | #define CMARK_API_TEST_CPLUSPLUS_H 3 | 4 | #include "harness.h" 5 | 6 | #ifdef __cplusplus 7 | extern "C" { 8 | #endif 9 | 10 | void test_cplusplus(test_batch_runner *runner); 11 | 12 | #ifdef __cplusplus 13 | } 14 | #endif 15 | 16 | #endif 17 | -------------------------------------------------------------------------------- /deps/cmark/api_test/harness.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_API_TEST_HARNESS_H 2 | #define CMARK_API_TEST_HARNESS_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | typedef struct { 9 | int test_num; 10 | int num_passed; 11 | int num_failed; 12 | int num_skipped; 13 | } test_batch_runner; 14 | 15 | test_batch_runner *test_batch_runner_new(); 16 | 17 | void SKIP(test_batch_runner *runner, int num_tests); 18 | 19 | void OK(test_batch_runner *runner, int cond, const char *msg, ...); 20 | 21 | void INT_EQ(test_batch_runner *runner, int got, int expected, const char *msg, 22 | ...); 23 | 24 | void STR_EQ(test_batch_runner *runner, const char *got, const char *expected, 25 | const char *msg, ...); 26 | 27 | int test_ok(test_batch_runner *runner); 28 | 29 | void test_print_summary(test_batch_runner *runner); 30 | 31 | #ifdef __cplusplus 32 | } 33 | #endif 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /deps/cmark/appveyor.yml: -------------------------------------------------------------------------------- 1 | environment: 2 | PYTHON: "C:\\Python34-x64" 3 | PYTHON_VERSION: "3.4.3" 4 | PYTHON_ARCH: "64" 5 | matrix: 6 | - MSVC_VERSION: 10 7 | - MSVC_VERSION: 12 8 | 9 | # set up for nmake: 10 | install: 11 | - "SET PATH=%PYTHON%;%PYTHON%\\Scripts;%PATH%" 12 | 13 | build_script: 14 | - 'tools\appveyor-build.bat' 15 | 16 | test_script: 17 | - 'nmake test' 18 | -------------------------------------------------------------------------------- /deps/cmark/bench/stats.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import sys 4 | import statistics 5 | 6 | def pairs(l, n): 7 | return zip(*[l[i::n] for i in range(n)]) 8 | 9 | # data comes in pairs: 10 | # n - time for running the program with no input 11 | # m - time for running it with the benchmark input 12 | # we measure (m - n) 13 | 14 | values = [ float(y) - float(x) for (x,y) in pairs(sys.stdin.readlines(),2)] 15 | 16 | print("mean = %.4f, median = %.4f, stdev = %.4f" % 17 | (statistics.mean(values), statistics.median(values), 18 | statistics.stdev(values))) 19 | 20 | -------------------------------------------------------------------------------- /deps/cmark/benchmarks.md: -------------------------------------------------------------------------------- 1 | # Benchmarks 2 | 3 | Here are some benchmarks, run on an ancient Thinkpad running Intel 4 | Core 2 Duo at 2GHz. The input text is a 11MB Markdown file built by 5 | concatenating the Markdown sources of all the localizations of the 6 | first edition of 7 | [*Pro Git*](https://github.com/progit/progit/tree/master/en) by Scott 8 | Chacon. 9 | 10 | |Implementation | Time (sec)| 11 | |-------------------|-----------:| 12 | | Markdown.pl | 2921.24 | 13 | | Python markdown | 291.25 | 14 | | PHP markdown | 20.82 | 15 | | kramdown | 17.32 | 16 | | cheapskate | 8.24 | 17 | | peg-markdown | 5.45 | 18 | | parsedown | 5.06 | 19 | | **commonmark.js** | 2.09 | 20 | | marked | 1.99 | 21 | | discount | 1.85 | 22 | | **cmark** | 0.29 | 23 | | hoedown | 0.21 | 24 | 25 | To run these benchmarks, use `make bench PROG=/path/to/program`. 26 | 27 | `time` is used to measure execution speed. The reported 28 | time is the *difference* between the time to run the program 29 | with the benchmark input and the time to run it with no input. 30 | (This procedure ensures that implementations in dynamic languages are 31 | not penalized by startup time.) A median of ten runs is taken. The 32 | process is reniced to a high priority so that the system doesn't 33 | interrupt runs. 34 | -------------------------------------------------------------------------------- /deps/cmark/data/CaseFolding-3.2.0.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/deps/cmark/data/CaseFolding-3.2.0.txt -------------------------------------------------------------------------------- /deps/cmark/man/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | if (NOT MSVC) 2 | 3 | include(GNUInstallDirs) 4 | 5 | install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/man1/cmark.1 6 | DESTINATION ${CMAKE_INSTALL_MANDIR}/man1) 7 | 8 | install(FILES ${CMAKE_CURRENT_SOURCE_DIR}/man3/cmark.3 9 | DESTINATION ${CMAKE_INSTALL_MANDIR}/man3) 10 | endif(NOT MSVC) 11 | -------------------------------------------------------------------------------- /deps/cmark/nmake.bat: -------------------------------------------------------------------------------- 1 | @nmake.exe /nologo /f Makefile.nmake %* 2 | -------------------------------------------------------------------------------- /deps/cmark/src/cmark.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include "node.h" 5 | #include "houdini.h" 6 | #include "cmark.h" 7 | #include "buffer.h" 8 | 9 | int cmark_version() { return CMARK_VERSION; } 10 | 11 | const char *cmark_version_string() { return CMARK_VERSION_STRING; } 12 | 13 | static void *xcalloc(size_t nmem, size_t size) { 14 | void *ptr = calloc(nmem, size); 15 | if (!ptr) abort(); 16 | return ptr; 17 | } 18 | 19 | static void *xrealloc(void *ptr, size_t size) { 20 | void *new_ptr = realloc(ptr, size); 21 | if (!new_ptr) abort(); 22 | return new_ptr; 23 | } 24 | 25 | cmark_mem DEFAULT_MEM_ALLOCATOR = { xcalloc, xrealloc, free }; 26 | 27 | char *cmark_markdown_to_html(const char *text, size_t len, int options) { 28 | cmark_node *doc; 29 | char *result; 30 | 31 | doc = cmark_parse_document(text, len, options); 32 | 33 | result = cmark_render_html(doc, options); 34 | cmark_node_free(doc); 35 | 36 | return result; 37 | } 38 | -------------------------------------------------------------------------------- /deps/cmark/src/cmark_ctype.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include "cmark_ctype.h" 4 | 5 | /** 1 = space, 2 = punct, 3 = digit, 4 = alpha, 0 = other 6 | */ 7 | static const uint8_t cmark_ctype_class[256] = { 8 | /* 0 1 2 3 4 5 6 7 8 9 a b c d e f */ 9 | /* 0 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0, 10 | /* 1 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 11 | /* 2 */ 1, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 12 | /* 3 */ 3, 3, 3, 3, 3, 3, 3, 3, 3, 3, 2, 2, 2, 2, 2, 2, 13 | /* 4 */ 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 14 | /* 5 */ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, 2, 2, 15 | /* 6 */ 2, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 16 | /* 7 */ 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 2, 2, 2, 2, 0, 17 | /* 8 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 18 | /* 9 */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 19 | /* a */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 20 | /* b */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 21 | /* c */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 22 | /* d */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 23 | /* e */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 24 | /* f */ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; 25 | 26 | /** 27 | * Returns 1 if c is a "whitespace" character as defined by the spec. 28 | */ 29 | int cmark_isspace(char c) { return cmark_ctype_class[(uint8_t)c] == 1; } 30 | 31 | /** 32 | * Returns 1 if c is an ascii punctuation character. 33 | */ 34 | int cmark_ispunct(char c) { return cmark_ctype_class[(uint8_t)c] == 2; } 35 | 36 | int cmark_isalnum(char c) { 37 | uint8_t result; 38 | result = cmark_ctype_class[(uint8_t)c]; 39 | return (result == 3 || result == 4); 40 | } 41 | 42 | int cmark_isdigit(char c) { return cmark_ctype_class[(uint8_t)c] == 3; } 43 | 44 | int cmark_isalpha(char c) { return cmark_ctype_class[(uint8_t)c] == 4; } 45 | -------------------------------------------------------------------------------- /deps/cmark/src/cmark_ctype.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_CMARK_CTYPE_H 2 | #define CMARK_CMARK_CTYPE_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | /** Locale-independent versions of functions from ctype.h. 9 | * We want cmark to behave the same no matter what the system locale. 10 | */ 11 | 12 | int cmark_isspace(char c); 13 | 14 | int cmark_ispunct(char c); 15 | 16 | int cmark_isalnum(char c); 17 | 18 | int cmark_isdigit(char c); 19 | 20 | int cmark_isalpha(char c); 21 | 22 | #ifdef __cplusplus 23 | } 24 | #endif 25 | 26 | #endif 27 | -------------------------------------------------------------------------------- /deps/cmark/src/cmark_version.h.in: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_VERSION_H 2 | #define CMARK_VERSION_H 3 | 4 | #define CMARK_VERSION ((@PROJECT_VERSION_MAJOR@ << 16) | (@PROJECT_VERSION_MINOR@ << 8) | @PROJECT_VERSION_PATCH@) 5 | #define CMARK_VERSION_STRING "@PROJECT_VERSION_MAJOR@.@PROJECT_VERSION_MINOR@.@PROJECT_VERSION_PATCH@" 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /deps/cmark/src/config.h.in: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_CONFIG_H 2 | #define CMARK_CONFIG_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | #cmakedefine HAVE_STDBOOL_H 9 | 10 | #ifdef HAVE_STDBOOL_H 11 | #include 12 | #elif !defined(__cplusplus) 13 | typedef char bool; 14 | #endif 15 | 16 | #cmakedefine HAVE___BUILTIN_EXPECT 17 | 18 | #cmakedefine HAVE___ATTRIBUTE__ 19 | 20 | #ifdef HAVE___ATTRIBUTE__ 21 | #define CMARK_ATTRIBUTE(list) __attribute__ (list) 22 | #else 23 | #define CMARK_ATTRIBUTE(list) 24 | #endif 25 | 26 | #ifndef CMARK_INLINE 27 | #if defined(_MSC_VER) && !defined(__cplusplus) 28 | #define CMARK_INLINE __inline 29 | #else 30 | #define CMARK_INLINE inline 31 | #endif 32 | #endif 33 | 34 | /* snprintf and vsnprintf fallbacks for MSVC before 2015, 35 | due to Valentin Milea http://stackoverflow.com/questions/2915672/ 36 | */ 37 | 38 | #if defined(_MSC_VER) && _MSC_VER < 1900 39 | 40 | #include 41 | #include 42 | 43 | #define snprintf c99_snprintf 44 | #define vsnprintf c99_vsnprintf 45 | 46 | CMARK_INLINE int c99_vsnprintf(char *outBuf, size_t size, const char *format, va_list ap) 47 | { 48 | int count = -1; 49 | 50 | if (size != 0) 51 | count = _vsnprintf_s(outBuf, size, _TRUNCATE, format, ap); 52 | if (count == -1) 53 | count = _vscprintf(format, ap); 54 | 55 | return count; 56 | } 57 | 58 | CMARK_INLINE int c99_snprintf(char *outBuf, size_t size, const char *format, ...) 59 | { 60 | int count; 61 | va_list ap; 62 | 63 | va_start(ap, format); 64 | count = c99_vsnprintf(outBuf, size, format, ap); 65 | va_end(ap); 66 | 67 | return count; 68 | } 69 | 70 | #endif 71 | 72 | #ifdef _WIN32 73 | # include 74 | typedef SSIZE_T ssize_t; 75 | typedef SIZE_T size_t; 76 | #else 77 | # include 78 | #endif 79 | 80 | #ifdef __cplusplus 81 | } 82 | #endif 83 | 84 | #endif 85 | -------------------------------------------------------------------------------- /deps/cmark/src/houdini.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_HOUDINI_H 2 | #define CMARK_HOUDINI_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | #include 9 | #include "config.h" 10 | #include "buffer.h" 11 | 12 | #ifdef HAVE___BUILTIN_EXPECT 13 | #define likely(x) __builtin_expect((x), 1) 14 | #define unlikely(x) __builtin_expect((x), 0) 15 | #else 16 | #define likely(x) (x) 17 | #define unlikely(x) (x) 18 | #endif 19 | 20 | #ifdef HOUDINI_USE_LOCALE 21 | #define _isxdigit(c) isxdigit(c) 22 | #define _isdigit(c) isdigit(c) 23 | #else 24 | /* 25 | * Helper _isdigit methods -- do not trust the current locale 26 | * */ 27 | #define _isxdigit(c) (strchr("0123456789ABCDEFabcdef", (c)) != NULL) 28 | #define _isdigit(c) ((c) >= '0' && (c) <= '9') 29 | #endif 30 | 31 | #define HOUDINI_ESCAPED_SIZE(x) (((x)*12) / 10) 32 | #define HOUDINI_UNESCAPED_SIZE(x) (x) 33 | 34 | extern bufsize_t houdini_unescape_ent(cmark_strbuf *ob, const uint8_t *src, 35 | bufsize_t size); 36 | extern int houdini_escape_html(cmark_strbuf *ob, const uint8_t *src, 37 | bufsize_t size); 38 | extern int houdini_escape_html0(cmark_strbuf *ob, const uint8_t *src, 39 | bufsize_t size, int secure); 40 | extern int houdini_unescape_html(cmark_strbuf *ob, const uint8_t *src, 41 | bufsize_t size); 42 | extern void houdini_unescape_html_f(cmark_strbuf *ob, const uint8_t *src, 43 | bufsize_t size); 44 | extern int houdini_escape_href(cmark_strbuf *ob, const uint8_t *src, 45 | bufsize_t size); 46 | 47 | #ifdef __cplusplus 48 | } 49 | #endif 50 | 51 | #endif 52 | -------------------------------------------------------------------------------- /deps/cmark/src/inlines.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_INLINES_H 2 | #define CMARK_INLINES_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | cmark_chunk cmark_clean_url(cmark_mem *mem, cmark_chunk *url); 9 | cmark_chunk cmark_clean_title(cmark_mem *mem, cmark_chunk *title); 10 | 11 | void cmark_parse_inlines(cmark_mem *mem, cmark_node *parent, cmark_reference_map *refmap, 12 | int options); 13 | 14 | bufsize_t cmark_parse_reference_inline(cmark_mem *mem, cmark_strbuf *input, 15 | cmark_reference_map *refmap); 16 | 17 | #ifdef __cplusplus 18 | } 19 | #endif 20 | 21 | #endif 22 | -------------------------------------------------------------------------------- /deps/cmark/src/iterator.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_ITERATOR_H 2 | #define CMARK_ITERATOR_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | #include "cmark.h" 9 | #include "memory.h" 10 | 11 | typedef struct { 12 | cmark_event_type ev_type; 13 | cmark_node *node; 14 | } cmark_iter_state; 15 | 16 | struct cmark_iter { 17 | cmark_mem *mem; 18 | cmark_node *root; 19 | cmark_iter_state cur; 20 | cmark_iter_state next; 21 | }; 22 | 23 | #ifdef __cplusplus 24 | } 25 | #endif 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /deps/cmark/src/libcmark.pc.in: -------------------------------------------------------------------------------- 1 | prefix=@CMAKE_INSTALL_PREFIX@ 2 | exec_prefix=@CMAKE_INSTALL_PREFIX@ 3 | libdir=@CMAKE_INSTALL_PREFIX@/lib 4 | includedir=@CMAKE_INSTALL_PREFIX@/include 5 | 6 | Name: libcmark 7 | Description: CommonMark parsing, rendering, and manipulation 8 | Version: @PROJECT_VERSION@ 9 | Libs: -L${libdir} -lcmark 10 | Cflags: -I${includedir} 11 | -------------------------------------------------------------------------------- /deps/cmark/src/node.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_NODE_H 2 | #define CMARK_NODE_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | #include 9 | #include 10 | 11 | #include "cmark.h" 12 | #include "buffer.h" 13 | #include "chunk.h" 14 | 15 | typedef struct { 16 | cmark_list_type list_type; 17 | int marker_offset; 18 | int padding; 19 | int start; 20 | cmark_delim_type delimiter; 21 | unsigned char bullet_char; 22 | bool tight; 23 | } cmark_list; 24 | 25 | typedef struct { 26 | cmark_chunk info; 27 | cmark_chunk literal; 28 | uint8_t fence_length; 29 | uint8_t fence_offset; 30 | unsigned char fence_char; 31 | int8_t fenced; 32 | } cmark_code; 33 | 34 | typedef struct { 35 | int level; 36 | bool setext; 37 | } cmark_heading; 38 | 39 | typedef struct { 40 | cmark_chunk url; 41 | cmark_chunk title; 42 | } cmark_link; 43 | 44 | typedef struct { 45 | cmark_chunk on_enter; 46 | cmark_chunk on_exit; 47 | } cmark_custom; 48 | 49 | enum cmark_node__internal_flags { 50 | CMARK_NODE__OPEN = (1 << 0), 51 | CMARK_NODE__LAST_LINE_BLANK = (1 << 1), 52 | }; 53 | 54 | struct cmark_node { 55 | cmark_strbuf content; 56 | 57 | struct cmark_node *next; 58 | struct cmark_node *prev; 59 | struct cmark_node *parent; 60 | struct cmark_node *first_child; 61 | struct cmark_node *last_child; 62 | 63 | void *user_data; 64 | 65 | int start_line; 66 | int start_column; 67 | int end_line; 68 | int end_column; 69 | uint16_t type; 70 | uint16_t flags; 71 | 72 | union { 73 | cmark_chunk literal; 74 | cmark_list list; 75 | cmark_code code; 76 | cmark_heading heading; 77 | cmark_link link; 78 | cmark_custom custom; 79 | int html_block_type; 80 | } as; 81 | }; 82 | 83 | static CMARK_INLINE cmark_mem *cmark_node_mem(cmark_node *node) { 84 | return node->content.mem; 85 | } 86 | CMARK_EXPORT int cmark_node_check(cmark_node *node, FILE *out); 87 | 88 | #ifdef __cplusplus 89 | } 90 | #endif 91 | 92 | #endif 93 | -------------------------------------------------------------------------------- /deps/cmark/src/parser.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_AST_H 2 | #define CMARK_AST_H 3 | 4 | #include 5 | #include "node.h" 6 | #include "buffer.h" 7 | #include "memory.h" 8 | 9 | #ifdef __cplusplus 10 | extern "C" { 11 | #endif 12 | 13 | #define MAX_LINK_LABEL_LENGTH 1000 14 | 15 | struct cmark_parser { 16 | struct cmark_mem *mem; 17 | struct cmark_reference_map *refmap; 18 | struct cmark_node *root; 19 | struct cmark_node *current; 20 | int line_number; 21 | bufsize_t offset; 22 | bufsize_t column; 23 | bufsize_t first_nonspace; 24 | bufsize_t first_nonspace_column; 25 | int indent; 26 | bool blank; 27 | bool partially_consumed_tab; 28 | cmark_strbuf curline; 29 | bufsize_t last_line_length; 30 | cmark_strbuf linebuf; 31 | int options; 32 | bool last_buffer_ended_with_cr; 33 | }; 34 | 35 | #ifdef __cplusplus 36 | } 37 | #endif 38 | 39 | #endif 40 | -------------------------------------------------------------------------------- /deps/cmark/src/references.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_REFERENCES_H 2 | #define CMARK_REFERENCES_H 3 | 4 | #include "memory.h" 5 | #include "chunk.h" 6 | 7 | #ifdef __cplusplus 8 | extern "C" { 9 | #endif 10 | 11 | #define REFMAP_SIZE 16 12 | 13 | struct cmark_reference { 14 | struct cmark_reference *next; 15 | unsigned char *label; 16 | cmark_chunk url; 17 | cmark_chunk title; 18 | unsigned int hash; 19 | }; 20 | 21 | typedef struct cmark_reference cmark_reference; 22 | 23 | struct cmark_reference_map { 24 | cmark_mem *mem; 25 | cmark_reference *table[REFMAP_SIZE]; 26 | }; 27 | 28 | typedef struct cmark_reference_map cmark_reference_map; 29 | 30 | cmark_reference_map *cmark_reference_map_new(cmark_mem *mem); 31 | void cmark_reference_map_free(cmark_reference_map *map); 32 | cmark_reference *cmark_reference_lookup(cmark_reference_map *map, 33 | cmark_chunk *label); 34 | extern void cmark_reference_create(cmark_reference_map *map, cmark_chunk *label, 35 | cmark_chunk *url, cmark_chunk *title); 36 | 37 | #ifdef __cplusplus 38 | } 39 | #endif 40 | 41 | #endif 42 | -------------------------------------------------------------------------------- /deps/cmark/src/render.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_RENDER_H 2 | #define CMARK_RENDER_H 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | 8 | #include 9 | #include "buffer.h" 10 | #include "chunk.h" 11 | #include "memory.h" 12 | 13 | typedef enum { LITERAL, NORMAL, TITLE, URL } cmark_escaping; 14 | 15 | struct cmark_renderer { 16 | cmark_mem *mem; 17 | cmark_strbuf *buffer; 18 | cmark_strbuf *prefix; 19 | int column; 20 | int width; 21 | int need_cr; 22 | bufsize_t last_breakable; 23 | bool begin_line; 24 | bool begin_content; 25 | bool no_linebreaks; 26 | bool in_tight_list_item; 27 | void (*outc)(struct cmark_renderer *, cmark_escaping, int32_t, unsigned char); 28 | void (*cr)(struct cmark_renderer *); 29 | void (*blankline)(struct cmark_renderer *); 30 | void (*out)(struct cmark_renderer *, const char *, bool, cmark_escaping); 31 | }; 32 | 33 | typedef struct cmark_renderer cmark_renderer; 34 | 35 | void cmark_render_ascii(cmark_renderer *renderer, const char *s); 36 | 37 | void cmark_render_code_point(cmark_renderer *renderer, uint32_t c); 38 | 39 | char *cmark_render(cmark_node *root, int options, int width, 40 | void (*outc)(cmark_renderer *, cmark_escaping, int32_t, 41 | unsigned char), 42 | int (*render_node)(cmark_renderer *renderer, 43 | cmark_node *node, 44 | cmark_event_type ev_type, int options)); 45 | 46 | #ifdef __cplusplus 47 | } 48 | #endif 49 | 50 | #endif 51 | -------------------------------------------------------------------------------- /deps/cmark/src/utf8.h: -------------------------------------------------------------------------------- 1 | #ifndef CMARK_UTF8_H 2 | #define CMARK_UTF8_H 3 | 4 | #include 5 | #include "buffer.h" 6 | 7 | #ifdef __cplusplus 8 | extern "C" { 9 | #endif 10 | 11 | void cmark_utf8proc_case_fold(cmark_strbuf *dest, const uint8_t *str, 12 | bufsize_t len); 13 | void cmark_utf8proc_encode_char(int32_t uc, cmark_strbuf *buf); 14 | int cmark_utf8proc_iterate(const uint8_t *str, bufsize_t str_len, int32_t *dst); 15 | void cmark_utf8proc_check(cmark_strbuf *dest, const uint8_t *line, 16 | bufsize_t size); 17 | int cmark_utf8proc_is_space(int32_t uc); 18 | int cmark_utf8proc_is_punctuation(int32_t uc); 19 | 20 | #ifdef __cplusplus 21 | } 22 | #endif 23 | 24 | #endif 25 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/asterisk: -------------------------------------------------------------------------------- 1 | * -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/attr_generic: -------------------------------------------------------------------------------- 1 | a="1" -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/attr_href: -------------------------------------------------------------------------------- 1 | href="1" -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/attr_xml_lang: -------------------------------------------------------------------------------- 1 | xml:lang="1" -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/attr_xmlns: -------------------------------------------------------------------------------- 1 | xmlns="1" -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/backslash: -------------------------------------------------------------------------------- 1 | \ -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/backtick: -------------------------------------------------------------------------------- 1 | ` -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/colon: -------------------------------------------------------------------------------- 1 | : -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/dashes: -------------------------------------------------------------------------------- 1 | --- -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/double_quote: -------------------------------------------------------------------------------- 1 | " -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/entity_builtin: -------------------------------------------------------------------------------- 1 | < -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/entity_decimal: -------------------------------------------------------------------------------- 1 |  -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/entity_external: -------------------------------------------------------------------------------- 1 | &a; -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/entity_hex: -------------------------------------------------------------------------------- 1 |  -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/equals: -------------------------------------------------------------------------------- 1 | === -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/exclamation: -------------------------------------------------------------------------------- 1 | ! -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/greater_than: -------------------------------------------------------------------------------- 1 | > -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/hash: -------------------------------------------------------------------------------- 1 | # -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/hyphen: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/deps/cmark/test/afl_dictionary/hyphen -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/indent: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/left_bracket: -------------------------------------------------------------------------------- 1 | [ -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/left_paren: -------------------------------------------------------------------------------- 1 | ( -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/less_than: -------------------------------------------------------------------------------- 1 | < -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/plus: -------------------------------------------------------------------------------- 1 | + -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/right_bracket: -------------------------------------------------------------------------------- 1 | ] -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/right_paren: -------------------------------------------------------------------------------- 1 | ) -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/single_quote: -------------------------------------------------------------------------------- 1 | ' -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_any: -------------------------------------------------------------------------------- 1 | ANY -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_brackets: -------------------------------------------------------------------------------- 1 | [] -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_cdata: -------------------------------------------------------------------------------- 1 | CDATA -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_dashes: -------------------------------------------------------------------------------- 1 | -- -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_empty_dblquotes: -------------------------------------------------------------------------------- 1 | "" -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_empty_quotes: -------------------------------------------------------------------------------- 1 | '' -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_idrefs: -------------------------------------------------------------------------------- 1 | IDREFS -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_parentheses: -------------------------------------------------------------------------------- 1 | () -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/string_pcdata: -------------------------------------------------------------------------------- 1 | #PCDATA -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/tag_cdata: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/tag_doctype: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/tag_open_close: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/tag_open_exclamation: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/tag_xml_q: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /deps/cmark/test/afl_dictionary/underscore: -------------------------------------------------------------------------------- 1 | _ -------------------------------------------------------------------------------- /deps/cmark/test/afl_test_cases/test.md: -------------------------------------------------------------------------------- 1 | # H1 2 | 3 | H2 4 | -- 5 | 6 | t ☺ 7 | *b* **em** `c` 8 | ≥\&\ 9 | \_e\_ 10 | 11 | 4) I1 12 | 13 | 5) I2 14 | > [l](/u "t") 15 | > 16 | > - [f] 17 | > - ![a](/u "t") 18 | > 19 | >> 20 | >> 21 | 22 | ~~~ l☺ 23 | cb 24 | ~~~ 25 | 26 | c1 27 | c2 28 | 29 | *** 30 | 31 |
32 | x 33 |
34 | 35 | [f]: /u "t" 36 | 37 | -------------------------------------------------------------------------------- /deps/cmark/test/regression.txt: -------------------------------------------------------------------------------- 1 | ### Regression tests 2 | 3 | Issue #113: EOL character weirdness on Windows 4 | (Important: first line ends with CR + CR + LF) 5 | 6 | ```````````````````````````````` example 7 | line1 8 | line2 9 | . 10 |

line1

11 |

line2

12 | ```````````````````````````````` 13 | 14 | Issue #114: cmark skipping first character in line 15 | (Important: the blank lines around "Repeatedly" contain a tab.) 16 | 17 | ```````````````````````````````` example 18 | By taking it apart 19 | 20 | - alternative solutions 21 | → 22 | Repeatedly solving 23 | → 24 | - how techniques 25 | . 26 |

By taking it apart

27 |
    28 |
  • alternative solutions
  • 29 |
30 |

Repeatedly solving

31 |
    32 |
  • how techniques
  • 33 |
34 | ```````````````````````````````` 35 | -------------------------------------------------------------------------------- /deps/cmark/toolchain-mingw32.cmake: -------------------------------------------------------------------------------- 1 | # the name of the target operating system 2 | SET(CMAKE_SYSTEM_NAME Windows) 3 | 4 | # which compilers to use for C and C++ 5 | SET(CMAKE_C_COMPILER i586-mingw32msvc-gcc) 6 | SET(CMAKE_CXX_COMPILER i586-mingw32msvc-g++) 7 | SET(CMAKE_RC_COMPILER i586-mingw32msvc-windres) 8 | 9 | # here is the target environment located 10 | SET(CMAKE_FIND_ROOT_PATH /usr/i586-mingw32msvc "${CMAKE_SOURCE_DIR}/windows") 11 | 12 | # adjust the default behaviour of the FIND_XXX() commands: 13 | # search headers and libraries in the target environment, search 14 | # programs in the host environment 15 | set(CMAKE_FIND_ROOT_PATH_MODE_PROGRAM NEVER) 16 | set(CMAKE_FIND_ROOT_PATH_MODE_LIBRARY ONLY) 17 | set(CMAKE_FIND_ROOT_PATH_MODE_INCLUDE ONLY) 18 | -------------------------------------------------------------------------------- /deps/cmark/tools/appveyor-build.bat: -------------------------------------------------------------------------------- 1 | @echo off 2 | 3 | if "%MSVC_VERSION%" == "10" goto msvc10 4 | 5 | call "C:\Program Files (x86)\Microsoft Visual Studio %MSVC_VERSION%.0\VC\vcvarsall.bat" amd64 6 | goto build 7 | 8 | :msvc10 9 | call "C:\Program Files\Microsoft SDKs\Windows\v7.1\Bin\SetEnv.cmd" /x64 10 | 11 | :build 12 | nmake 13 | 14 | -------------------------------------------------------------------------------- /deps/cmark/tools/make_entities_inc.py: -------------------------------------------------------------------------------- 1 | # Creates C data structures for binary lookup table of entities, 2 | # using python's html5 entity data. 3 | # Usage: python3 tools/make_entities_inc.py > src/entities.inc 4 | 5 | import html 6 | 7 | entities5 = html.entities.html5 8 | 9 | # remove keys without semicolons. For some reason the list 10 | # has duplicates of a few things, like auml, one with and one 11 | # without a semicolon. 12 | entities = sorted([(k[:-1], entities5[k].encode('utf-8')) for k in entities5.keys() if k[-1] == ';']) 13 | 14 | # Print out the header: 15 | print("""/* Autogenerated by tools/make_headers_inc.py */ 16 | 17 | struct cmark_entity_node { 18 | unsigned char *entity; 19 | unsigned char bytes[8]; 20 | }; 21 | 22 | #define CMARK_ENTITY_MIN_LENGTH 2 23 | #define CMARK_ENTITY_MAX_LENGTH 31""") 24 | 25 | print("#define CMARK_NUM_ENTITIES " + str(len(entities))); 26 | 27 | print("\nstatic const struct cmark_entity_node cmark_entities[] = {"); 28 | 29 | for (ent, bs) in entities: 30 | print('{(unsigned char*)"' + ent + '", {' + ', '.join(map(str, bs)) + ', 0}},') 31 | 32 | print("};") 33 | -------------------------------------------------------------------------------- /deps/cmark/tools/mkcasefold.pl: -------------------------------------------------------------------------------- 1 | binmode STDOUT; 2 | print(" switch (c) {\n"); 3 | my $lastchar = ""; 4 | while () { 5 | if (/^[A-F0-9]/ and / [CF]; /) { 6 | my ($char, $type, $subst) = m/([A-F0-9]+); ([CF]); ([^;]+)/; 7 | if ($char eq $lastchar) { 8 | break; 9 | } 10 | my @subst = $subst =~ m/(\w+)/g; 11 | printf(" case 0x%s:\n", $char); 12 | foreach (@subst) { 13 | printf(" bufpush(0x%s);\n", $_); 14 | } 15 | printf(" break;\n"); 16 | $lastchar = $char; 17 | } 18 | } 19 | printf(" default:\n"); 20 | printf(" bufpush(c);\n"); 21 | print(" }\n"); 22 | 23 | -------------------------------------------------------------------------------- /deps/cmark/wrappers/wrapper.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | # Example for using the shared library from python 4 | # Will work with either python 2 or python 3 5 | # Requires cmark library to be installed 6 | 7 | from ctypes import CDLL, c_char_p, c_long 8 | import sys 9 | import platform 10 | 11 | sysname = platform.system() 12 | 13 | if sysname == 'Darwin': 14 | libname = "libcmark.dylib" 15 | elif sysname == 'Windows': 16 | libname = "cmark.dll" 17 | else: 18 | libname = "libcmark.so" 19 | cmark = CDLL(libname) 20 | 21 | markdown = cmark.cmark_markdown_to_html 22 | markdown.restype = c_char_p 23 | markdown.argtypes = [c_char_p, c_long, c_long] 24 | 25 | opts = 0 # defaults 26 | 27 | def md2html(text): 28 | if sys.version_info >= (3,0): 29 | textbytes = text.encode('utf-8') 30 | textlen = len(textbytes) 31 | return markdown(textbytes, textlen, opts).decode('utf-8') 32 | else: 33 | textbytes = text 34 | textlen = len(text) 35 | return markdown(textbytes, textlen, opts) 36 | 37 | sys.stdout.write(md2html(sys.stdin.read())) 38 | -------------------------------------------------------------------------------- /deps/cmark/wrappers/wrapper.rb: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env ruby 2 | require 'ffi' 3 | 4 | module CMark 5 | extend FFI::Library 6 | ffi_lib ['libcmark', 'cmark'] 7 | attach_function :cmark_markdown_to_html, [:string, :int, :int], :string 8 | end 9 | 10 | def markdown_to_html(s) 11 | len = s.bytesize 12 | CMark::cmark_markdown_to_html(s, len, 0) 13 | end 14 | 15 | STDOUT.write(markdown_to_html(ARGF.read())) 16 | -------------------------------------------------------------------------------- /deps/content-disposition/content-disposition.h: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int ContentDispositionParse(char const *const str, char **const type, char *values[], char const *const fields[], size_t const count); 4 | 5 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/LINKS: -------------------------------------------------------------------------------- 1 | New versions of this package (crypt_blowfish): 2 | 3 | http://www.openwall.com/crypt/ 4 | 5 | A paper on the algorithm that explains its design decisions: 6 | 7 | http://www.usenix.org/events/usenix99/provos.html 8 | 9 | Unix Seventh Edition Manual, Volume 2: the password scheme (1978): 10 | 11 | http://plan9.bell-labs.com/7thEdMan/vol2/password 12 | 13 | The Openwall GNU/*/Linux (Owl) tcb suite implementing the alternative 14 | password shadowing scheme. This includes a PAM module which 15 | supersedes pam_unix and uses the password hashing framework provided 16 | with crypt_blowfish when setting new passwords. 17 | 18 | http://www.openwall.com/tcb/ 19 | 20 | pam_passwdqc, a password strength checking and policy enforcement 21 | module for PAM-aware password changing programs: 22 | 23 | http://www.openwall.com/passwdqc/ 24 | 25 | John the Ripper password cracker: 26 | 27 | http://www.openwall.com/john/ 28 | 29 | $Owl: Owl/packages/glibc/crypt_blowfish/LINKS,v 1.4 2005/11/16 13:09:47 solar Exp $ 30 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/PERFORMANCE: -------------------------------------------------------------------------------- 1 | These numbers are for 32 iterations ("$2a$05"): 2 | 3 | OpenBSD 3.0 bcrypt(*) crypt_blowfish 0.4.4 4 | Pentium III, 840 MHz 99 c/s 121 c/s (+22%) 5 | Alpha 21164PC, 533 MHz 55.5 c/s 76.9 c/s (+38%) 6 | UltraSparc IIi, 400 MHz 49.9 c/s 52.5 c/s (+5%) 7 | Pentium, 120 MHz 8.8 c/s 20.1 c/s (+128%) 8 | PA-RISC 7100LC, 80 MHz 8.5 c/s 16.3 c/s (+92%) 9 | 10 | (*) built with -fomit-frame-pointer -funroll-loops, which I don't 11 | think happens for libcrypt. 12 | 13 | Starting with version 1.1 released in June 2011, default builds of 14 | crypt_blowfish invoke a quick self-test on every hash computation. 15 | This has roughly a 4.8% performance impact at "$2a$05", but only a 0.6% 16 | impact at a more typical setting of "$2a$08". 17 | 18 | The large speedup for the original Pentium is due to the assembly 19 | code and the weird optimizations this processor requires. 20 | 21 | The numbers for password cracking are 2 to 10% higher than those for 22 | crypt_blowfish as certain things may be done out of the loop and the 23 | code doesn't need to be reentrant. 24 | 25 | Recent versions of John the Ripper (1.6.25-dev and newer) achieve an 26 | additional 15% speedup on the Pentium Pro family of processors (which 27 | includes Pentium III) with a separate version of the assembly code and 28 | run-time CPU detection. 29 | 30 | $Owl: Owl/packages/glibc/crypt_blowfish/PERFORMANCE,v 1.6 2011/06/21 12:09:20 solar Exp $ 31 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/crypt.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Written by Solar Designer in 2000-2002. 3 | * No copyright is claimed, and the software is hereby placed in the public 4 | * domain. In case this attempt to disclaim copyright and place the software 5 | * in the public domain is deemed null and void, then the software is 6 | * Copyright (c) 2000-2002 Solar Designer and it is hereby released to the 7 | * general public under the following terms: 8 | * 9 | * Redistribution and use in source and binary forms, with or without 10 | * modification, are permitted. 11 | * 12 | * There's ABSOLUTELY NO WARRANTY, express or implied. 13 | * 14 | * See crypt_blowfish.c for more information. 15 | */ 16 | 17 | #include 18 | 19 | #if defined(_OW_SOURCE) || defined(__USE_OW) 20 | #define __SKIP_GNU 21 | #undef __SKIP_OW 22 | #include 23 | #undef __SKIP_GNU 24 | #endif 25 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/crypt_blowfish.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Written by Solar Designer in 2000-2011. 3 | * No copyright is claimed, and the software is hereby placed in the public 4 | * domain. In case this attempt to disclaim copyright and place the software 5 | * in the public domain is deemed null and void, then the software is 6 | * Copyright (c) 2000-2011 Solar Designer and it is hereby released to the 7 | * general public under the following terms: 8 | * 9 | * Redistribution and use in source and binary forms, with or without 10 | * modification, are permitted. 11 | * 12 | * There's ABSOLUTELY NO WARRANTY, express or implied. 13 | * 14 | * See crypt_blowfish.c for more information. 15 | */ 16 | 17 | #ifndef _CRYPT_BLOWFISH_H 18 | #define _CRYPT_BLOWFISH_H 19 | 20 | extern int _crypt_output_magic(const char *setting, char *output, int size); 21 | extern char *_crypt_blowfish_rn(const char *key, const char *setting, 22 | char *output, int size); 23 | extern char *_crypt_gensalt_blowfish_rn(const char *prefix, 24 | unsigned long count, 25 | const char *input, int size, char *output, int output_size); 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/crypt_gensalt.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Written by Solar Designer in 2000-2011. 3 | * No copyright is claimed, and the software is hereby placed in the public 4 | * domain. In case this attempt to disclaim copyright and place the software 5 | * in the public domain is deemed null and void, then the software is 6 | * Copyright (c) 2000-2011 Solar Designer and it is hereby released to the 7 | * general public under the following terms: 8 | * 9 | * Redistribution and use in source and binary forms, with or without 10 | * modification, are permitted. 11 | * 12 | * There's ABSOLUTELY NO WARRANTY, express or implied. 13 | * 14 | * See crypt_blowfish.c for more information. 15 | */ 16 | 17 | #ifndef _CRYPT_GENSALT_H 18 | #define _CRYPT_GENSALT_H 19 | 20 | extern unsigned char _crypt_itoa64[]; 21 | extern char *_crypt_gensalt_traditional_rn(const char *prefix, 22 | unsigned long count, 23 | const char *input, int size, char *output, int output_size); 24 | extern char *_crypt_gensalt_extended_rn(const char *prefix, 25 | unsigned long count, 26 | const char *input, int size, char *output, int output_size); 27 | extern char *_crypt_gensalt_md5_rn(const char *prefix, unsigned long count, 28 | const char *input, int size, char *output, int output_size); 29 | 30 | #endif 31 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/glibc-2.1.3-crypt.diff: -------------------------------------------------------------------------------- 1 | --- glibc-2.1.3.orig/crypt/sysdeps/unix/Makefile 1997-03-05 00:33:59 +0000 2 | +++ glibc-2.1.3/crypt/sysdeps/unix/Makefile 2000-06-11 03:13:41 +0000 3 | @@ -1,4 +1,4 @@ 4 | ifeq ($(subdir),md5-crypt) 5 | -libcrypt-routines += crypt crypt_util 6 | -dont_distribute += crypt.c crypt_util.c 7 | +libcrypt-routines += crypt crypt_util crypt_blowfish x86 crypt_gensalt wrapper 8 | +dont_distribute += crypt.c crypt_util.c crypt_blowfish.c x86.S crypt_gensalt.c wrapper.c 9 | endif 10 | --- glibc-2.1.3.orig/crypt/sysdeps/unix/crypt-entry.c 1998-12-10 12:49:04 +0000 11 | +++ glibc-2.1.3/crypt/sysdeps/unix/crypt-entry.c 2000-06-11 03:14:57 +0000 12 | @@ -70,7 +70,7 @@ extern struct crypt_data _ufc_foobar; 13 | */ 14 | 15 | char * 16 | -__crypt_r (key, salt, data) 17 | +__des_crypt_r (key, salt, data) 18 | const char *key; 19 | const char *salt; 20 | struct crypt_data * __restrict data; 21 | @@ -115,6 +115,7 @@ __crypt_r (key, salt, data) 22 | _ufc_output_conversion_r (res[0], res[1], salt, data); 23 | return data->crypt_3_buf; 24 | } 25 | +#if 0 26 | weak_alias (__crypt_r, crypt_r) 27 | 28 | char * 29 | @@ -147,3 +148,4 @@ __fcrypt (key, salt) 30 | return crypt (key, salt); 31 | } 32 | #endif 33 | +#endif 34 | --- glibc-2.1.3.orig/md5-crypt/Makefile 1998-07-02 22:46:47 +0000 35 | +++ glibc-2.1.3/md5-crypt/Makefile 2000-06-11 03:12:34 +0000 36 | @@ -21,7 +21,7 @@ 37 | # 38 | subdir := md5-crypt 39 | 40 | -headers := crypt.h 41 | +headers := crypt.h gnu-crypt.h ow-crypt.h 42 | 43 | distribute := md5.h 44 | 45 | --- glibc-2.1.3.orig/md5-crypt/Versions 1998-07-02 22:32:07 +0000 46 | +++ glibc-2.1.3/md5-crypt/Versions 2000-06-11 09:11:03 +0000 47 | @@ -1,5 +1,6 @@ 48 | libcrypt { 49 | GLIBC_2.0 { 50 | crypt; crypt_r; encrypt; encrypt_r; fcrypt; setkey; setkey_r; 51 | + crypt_rn; crypt_ra; crypt_gensalt; crypt_gensalt_rn; crypt_gensalt_ra; 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/glibc-2.3.6-crypt.diff: -------------------------------------------------------------------------------- 1 | --- glibc-2.3.6.orig/crypt/Makefile 2001-07-06 04:54:45 +0000 2 | +++ glibc-2.3.6/crypt/Makefile 2004-02-27 00:23:48 +0000 3 | @@ -21,14 +21,14 @@ 4 | # 5 | subdir := crypt 6 | 7 | -headers := crypt.h 8 | +headers := crypt.h gnu-crypt.h ow-crypt.h 9 | 10 | distribute := md5.h 11 | 12 | extra-libs := libcrypt 13 | extra-libs-others := $(extra-libs) 14 | 15 | -libcrypt-routines := crypt-entry md5-crypt md5 crypt crypt_util 16 | +libcrypt-routines := crypt-entry md5-crypt md5 crypt crypt_util crypt_blowfish x86 crypt_gensalt wrapper 17 | 18 | tests = cert md5test md5c-test 19 | 20 | --- glibc-2.3.6.orig/crypt/Versions 2000-03-04 00:47:30 +0000 21 | +++ glibc-2.3.6/crypt/Versions 2004-02-27 00:25:15 +0000 22 | @@ -1,5 +1,6 @@ 23 | libcrypt { 24 | GLIBC_2.0 { 25 | crypt; crypt_r; encrypt; encrypt_r; fcrypt; setkey; setkey_r; 26 | + crypt_rn; crypt_ra; crypt_gensalt; crypt_gensalt_rn; crypt_gensalt_ra; 27 | } 28 | } 29 | --- glibc-2.3.6.orig/crypt/crypt-entry.c 2001-07-06 05:18:49 +0000 30 | +++ glibc-2.3.6/crypt/crypt-entry.c 2004-02-27 00:12:32 +0000 31 | @@ -70,7 +70,7 @@ extern struct crypt_data _ufc_foobar; 32 | */ 33 | 34 | char * 35 | -__crypt_r (key, salt, data) 36 | +__des_crypt_r (key, salt, data) 37 | const char *key; 38 | const char *salt; 39 | struct crypt_data * __restrict data; 40 | @@ -115,6 +115,7 @@ __crypt_r (key, salt, data) 41 | _ufc_output_conversion_r (res[0], res[1], salt, data); 42 | return data->crypt_3_buf; 43 | } 44 | +#if 0 45 | weak_alias (__crypt_r, crypt_r) 46 | 47 | char * 48 | @@ -147,3 +148,4 @@ __fcrypt (key, salt) 49 | return crypt (key, salt); 50 | } 51 | #endif 52 | +#endif 53 | -------------------------------------------------------------------------------- /deps/crypt_blowfish/ow-crypt.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Written by Solar Designer in 2000-2011. 3 | * No copyright is claimed, and the software is hereby placed in the public 4 | * domain. In case this attempt to disclaim copyright and place the software 5 | * in the public domain is deemed null and void, then the software is 6 | * Copyright (c) 2000-2011 Solar Designer and it is hereby released to the 7 | * general public under the following terms: 8 | * 9 | * Redistribution and use in source and binary forms, with or without 10 | * modification, are permitted. 11 | * 12 | * There's ABSOLUTELY NO WARRANTY, express or implied. 13 | * 14 | * See crypt_blowfish.c for more information. 15 | */ 16 | 17 | #ifndef _OW_CRYPT_H 18 | #define _OW_CRYPT_H 19 | 20 | #ifndef __GNUC__ 21 | #undef __const 22 | #define __const const 23 | #endif 24 | 25 | #ifndef __SKIP_GNU 26 | extern char *crypt(__const char *key, __const char *setting); 27 | extern char *crypt_r(__const char *key, __const char *setting, void *data); 28 | #endif 29 | 30 | #ifndef __SKIP_OW 31 | extern char *crypt_rn(__const char *key, __const char *setting, 32 | void *data, int size); 33 | extern char *crypt_ra(__const char *key, __const char *setting, 34 | void **data, int *size); 35 | extern char *crypt_gensalt(__const char *prefix, unsigned long count, 36 | __const char *input, int size); 37 | extern char *crypt_gensalt_rn(__const char *prefix, unsigned long count, 38 | __const char *input, int size, char *output, int output_size); 39 | extern char *crypt_gensalt_ra(__const char *prefix, unsigned long count, 40 | __const char *input, int size); 41 | #endif 42 | 43 | #endif 44 | -------------------------------------------------------------------------------- /deps/fts3/fts3Int.h: -------------------------------------------------------------------------------- 1 | // All we need for the FTS Porter stemmer. 2 | 3 | /* 4 | ** Macro used to suppress compiler warnings for unused parameters. 5 | */ 6 | #define UNUSED_PARAMETER(x) (void)(x) 7 | 8 | -------------------------------------------------------------------------------- /deps/fts3/sqlite3.h: -------------------------------------------------------------------------------- 1 | // All we need for the FTS Porter stemmer. 2 | 3 | #define sqlite3_malloc malloc 4 | #define sqlite3_free free 5 | #define sqlite3_realloc realloc 6 | 7 | #define SQLITE_OK 0 8 | #define SQLITE_NOMEM 7 9 | #define SQLITE_DONE 101 10 | 11 | -------------------------------------------------------------------------------- /deps/memorymapping/deps.json: -------------------------------------------------------------------------------- 1 | {"NimbusKit":[],"Frameworks":[]} -------------------------------------------------------------------------------- /deps/memorymapping/src/NimbusMemoryMapping.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright 2011-2014 NimbusKit 3 | // 4 | // Licensed under the Apache License, Version 2.0 (the "License"); 5 | // you may not use this file except in compliance with the License. 6 | // You may obtain a copy of the License at 7 | // 8 | // http://www.apache.org/licenses/LICENSE-2.0 9 | // 10 | // Unless required by applicable law or agreed to in writing, software 11 | // distributed under the License is distributed on an "AS IS" BASIS, 12 | // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | // See the License for the specific language governing permissions and 14 | // limitations under the License. 15 | // 16 | 17 | #ifdef NIMBUSKIT_FRAMEWORK 18 | #import 19 | #else 20 | #import "fmemopen.h" 21 | #endif 22 | 23 | /** 24 | * @defgroup NimbusMemoryMappping Nimbus Memory Mapping 25 | * 26 | *
27 | * 28 | */ 29 | -------------------------------------------------------------------------------- /deps/memorymapping/src/fmemopen.h: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright 2011-2014 NimbusKit 3 | // Originally ported from https://github.com/ingenuitas/python-tesseract/blob/master/fmemopen.c 4 | // 5 | // Licensed under the Apache License, Version 2.0 (the "License"); 6 | // you may not use this file except in compliance with the License. 7 | // You may obtain a copy of the License at 8 | // 9 | // http://www.apache.org/licenses/LICENSE-2.0 10 | // 11 | // Unless required by applicable law or agreed to in writing, software 12 | // distributed under the License is distributed on an "AS IS" BASIS, 13 | // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 | // See the License for the specific language governing permissions and 15 | // limitations under the License. 16 | // 17 | 18 | #ifndef FMEMOPEN_H_ 19 | #define FMEMOPEN_H_ 20 | 21 | #if defined __cplusplus 22 | extern "C" { 23 | #endif 24 | 25 | /** 26 | * A BSD port of the fmemopen Linux method using funopen. 27 | * 28 | * man docs for fmemopen: 29 | * http://linux.die.net/man/3/fmemopen 30 | * 31 | * man docs for funopen: 32 | * https://developer.apple.com/library/mac/#documentation/Darwin/Reference/ManPages/man3/funopen.3.html 33 | * 34 | * This method is ported from ingenuitas' python-tesseract project. 35 | * 36 | * You must call fclose on the returned file pointer or memory will be leaked. 37 | * 38 | * @param buf The data that will be used to back the FILE* methods. Must be at least 39 | * @c size bytes. 40 | * @param size The size of the @c buf data. 41 | * @param mode The permitted stream operation modes. 42 | * @return A pointer that can be used in the fread/fwrite/fseek/fclose family of methods. 43 | * If a failure occurred NULL will be returned. 44 | * @ingroup NimbusMemoryMappping 45 | */ 46 | FILE *fmemopen(void *buf, size_t size, const char *mode); 47 | 48 | #ifdef __cplusplus 49 | } 50 | #endif 51 | 52 | #endif // #ifndef FMEMOPEN_H_ 53 | -------------------------------------------------------------------------------- /deps/smhasher/AvalancheTest.cpp: -------------------------------------------------------------------------------- 1 | #include "AvalancheTest.h" 2 | 3 | //----------------------------------------------------------------------------- 4 | 5 | void PrintAvalancheDiagram ( int x, int y, int reps, double scale, int * bins ) 6 | { 7 | const char * symbols = ".123456789X"; 8 | 9 | for(int i = 0; i < y; i++) 10 | { 11 | printf("["); 12 | for(int j = 0; j < x; j++) 13 | { 14 | int k = (y - i) -1; 15 | 16 | int bin = bins[k + (j*y)]; 17 | 18 | double b = double(bin) / double(reps); 19 | b = fabs(b*2 - 1); 20 | 21 | b *= scale; 22 | 23 | int s = (int)floor(b*10); 24 | 25 | if(s > 10) s = 10; 26 | if(s < 0) s = 0; 27 | 28 | printf("%c",symbols[s]); 29 | } 30 | 31 | printf("]\n"); 32 | } 33 | } 34 | 35 | //---------------------------------------------------------------------------- 36 | 37 | double maxBias ( std::vector & counts, int reps ) 38 | { 39 | double worst = 0; 40 | 41 | for(int i = 0; i < (int)counts.size(); i++) 42 | { 43 | double c = double(counts[i]) / double(reps); 44 | 45 | double d = fabs(c * 2 - 1); 46 | 47 | if(d > worst) 48 | { 49 | worst = d; 50 | } 51 | } 52 | 53 | return worst; 54 | } 55 | 56 | //----------------------------------------------------------------------------- 57 | -------------------------------------------------------------------------------- /deps/smhasher/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | project(SMHasher) 2 | 3 | cmake_minimum_required(VERSION 2.4) 4 | 5 | set(CMAKE_BUILD_TYPE Release) 6 | 7 | add_library( 8 | SMHasherSupport 9 | AvalancheTest.cpp 10 | Bitslice.cpp 11 | Bitvec.cpp 12 | CityTest.cpp 13 | City.cpp 14 | crc.cpp 15 | DifferentialTest.cpp 16 | Hashes.cpp 17 | KeysetTest.cpp 18 | lookup3.cpp 19 | md5.cpp 20 | MurmurHash1.cpp 21 | MurmurHash2.cpp 22 | MurmurHash3.cpp 23 | Platform.cpp 24 | Random.cpp 25 | sha1.cpp 26 | SpeedTest.cpp 27 | Spooky.cpp 28 | SpookyTest.cpp 29 | Stats.cpp 30 | SuperFastHash.cpp 31 | Types.cpp 32 | PMurHash.c 33 | ) 34 | 35 | add_executable( 36 | SMHasher 37 | main.cpp 38 | ) 39 | 40 | target_link_libraries( 41 | SMHasher 42 | SMHasherSupport 43 | ) 44 | -------------------------------------------------------------------------------- /deps/smhasher/CityTest.cpp: -------------------------------------------------------------------------------- 1 | #include "City.h" 2 | 3 | void CityHash64_test ( const void * key, int len, uint32_t seed, void * out ) 4 | { 5 | *(uint64*)out = CityHash64WithSeed((const char *)key,len,seed); 6 | } 7 | 8 | void CityHash128_test ( const void * key, int len, uint32_t seed, void * out ) 9 | { 10 | uint128 s(0,0); 11 | 12 | s.first = seed; 13 | 14 | *(uint128*)out = CityHash128WithSeed((const char*)key,len,s); 15 | } 16 | -------------------------------------------------------------------------------- /deps/smhasher/DifferentialTest.cpp: -------------------------------------------------------------------------------- 1 | #include "DifferentialTest.h" 2 | 3 | //---------------------------------------------------------------------------- 4 | -------------------------------------------------------------------------------- /deps/smhasher/MurmurHash1.h: -------------------------------------------------------------------------------- 1 | //----------------------------------------------------------------------------- 2 | // MurmurHash1 was written by Austin Appleby, and is placed in the public 3 | // domain. The author hereby disclaims copyright to this source code. 4 | 5 | #ifndef _MURMURHASH1_H_ 6 | #define _MURMURHASH1_H_ 7 | 8 | //----------------------------------------------------------------------------- 9 | // Platform-specific functions and macros 10 | 11 | // Microsoft Visual Studio 12 | 13 | #if defined(_MSC_VER) && (_MSC_VER < 1600) 14 | 15 | typedef unsigned char uint8_t; 16 | typedef unsigned int uint32_t; 17 | typedef unsigned __int64 uint64_t; 18 | 19 | // Other compilers 20 | 21 | #else // defined(_MSC_VER) 22 | 23 | #include 24 | 25 | #endif // !defined(_MSC_VER) 26 | 27 | //----------------------------------------------------------------------------- 28 | 29 | uint32_t MurmurHash1 ( const void * key, int len, uint32_t seed ); 30 | uint32_t MurmurHash1Aligned ( const void * key, int len, uint32_t seed ); 31 | 32 | //----------------------------------------------------------------------------- 33 | 34 | #endif // _MURMURHASH1_H_ 35 | -------------------------------------------------------------------------------- /deps/smhasher/MurmurHash2.h: -------------------------------------------------------------------------------- 1 | //----------------------------------------------------------------------------- 2 | // MurmurHash2 was written by Austin Appleby, and is placed in the public 3 | // domain. The author hereby disclaims copyright to this source code. 4 | 5 | #ifndef _MURMURHASH2_H_ 6 | #define _MURMURHASH2_H_ 7 | 8 | //----------------------------------------------------------------------------- 9 | // Platform-specific functions and macros 10 | 11 | // Microsoft Visual Studio 12 | 13 | #if defined(_MSC_VER) && (_MSC_VER < 1600) 14 | 15 | typedef unsigned char uint8_t; 16 | typedef unsigned int uint32_t; 17 | typedef unsigned __int64 uint64_t; 18 | 19 | // Other compilers 20 | 21 | #else // defined(_MSC_VER) 22 | 23 | #include 24 | 25 | #endif // !defined(_MSC_VER) 26 | 27 | //----------------------------------------------------------------------------- 28 | 29 | uint32_t MurmurHash2 ( const void * key, int len, uint32_t seed ); 30 | uint64_t MurmurHash64A ( const void * key, int len, uint64_t seed ); 31 | uint64_t MurmurHash64B ( const void * key, int len, uint64_t seed ); 32 | uint32_t MurmurHash2A ( const void * key, int len, uint32_t seed ); 33 | uint32_t MurmurHashNeutral2 ( const void * key, int len, uint32_t seed ); 34 | uint32_t MurmurHashAligned2 ( const void * key, int len, uint32_t seed ); 35 | 36 | //----------------------------------------------------------------------------- 37 | 38 | #endif // _MURMURHASH2_H_ 39 | 40 | -------------------------------------------------------------------------------- /deps/smhasher/MurmurHash3.h: -------------------------------------------------------------------------------- 1 | //----------------------------------------------------------------------------- 2 | // MurmurHash3 was written by Austin Appleby, and is placed in the public 3 | // domain. The author hereby disclaims copyright to this source code. 4 | 5 | #ifndef _MURMURHASH3_H_ 6 | #define _MURMURHASH3_H_ 7 | 8 | //----------------------------------------------------------------------------- 9 | // Platform-specific functions and macros 10 | 11 | // Microsoft Visual Studio 12 | 13 | #if defined(_MSC_VER) && (_MSC_VER < 1600) 14 | 15 | typedef unsigned char uint8_t; 16 | typedef unsigned int uint32_t; 17 | typedef unsigned __int64 uint64_t; 18 | 19 | // Other compilers 20 | 21 | #else // defined(_MSC_VER) 22 | 23 | #include 24 | 25 | #endif // !defined(_MSC_VER) 26 | 27 | //----------------------------------------------------------------------------- 28 | 29 | #ifdef __cplusplus 30 | extern "C" { 31 | #endif 32 | 33 | void MurmurHash3_x86_32 ( const void * key, int len, uint32_t seed, void * out ); 34 | 35 | void MurmurHash3_x86_128 ( const void * key, int len, uint32_t seed, void * out ); 36 | 37 | void MurmurHash3_x64_128 ( const void * key, int len, uint32_t seed, void * out ); 38 | 39 | #ifdef __cplusplus 40 | } 41 | #endif 42 | 43 | //----------------------------------------------------------------------------- 44 | 45 | #endif // _MURMURHASH3_H_ 46 | -------------------------------------------------------------------------------- /deps/smhasher/Platform.cpp: -------------------------------------------------------------------------------- 1 | #include "Platform.h" 2 | 3 | #include 4 | 5 | void testRDTSC ( void ) 6 | { 7 | int64_t temp = rdtsc(); 8 | 9 | printf("%d",(int)temp); 10 | } 11 | 12 | #if defined(_MSC_VER) 13 | 14 | #include 15 | 16 | void SetAffinity ( int cpu ) 17 | { 18 | SetProcessAffinityMask(GetCurrentProcess(),cpu); 19 | SetThreadPriority(GetCurrentThread(), THREAD_PRIORITY_HIGHEST); 20 | } 21 | 22 | #else 23 | 24 | #include 25 | 26 | void SetAffinity ( int /*cpu*/ ) 27 | { 28 | #if !defined(__CYGWIN__) && !defined(__APPLE__) 29 | cpu_set_t mask; 30 | 31 | CPU_ZERO(&mask); 32 | 33 | CPU_SET(2,&mask); 34 | 35 | if( sched_setaffinity(0,sizeof(mask),&mask) == -1) 36 | { 37 | printf("WARNING: Could not set CPU affinity\n"); 38 | } 39 | #endif 40 | } 41 | 42 | #endif 43 | -------------------------------------------------------------------------------- /deps/smhasher/Random.cpp: -------------------------------------------------------------------------------- 1 | #include "Random.h" 2 | 3 | Rand g_rand1(1); 4 | Rand g_rand2(2); 5 | Rand g_rand3(3); 6 | Rand g_rand4(4); 7 | 8 | //----------------------------------------------------------------------------- 9 | -------------------------------------------------------------------------------- /deps/smhasher/SpeedTest.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include "Types.h" 4 | 5 | void BulkSpeedTest ( pfHash hash, uint32_t seed ); 6 | void TinySpeedTest ( pfHash hash, int hashsize, int keysize, uint32_t seed, bool verbose, double & outCycles ); 7 | 8 | //----------------------------------------------------------------------------- 9 | -------------------------------------------------------------------------------- /deps/smhasher/SpookyTest.cpp: -------------------------------------------------------------------------------- 1 | #include "Spooky.h" 2 | 3 | void SpookyHash32_test(const void *key, int len, uint32_t seed, void *out) { 4 | *(uint32_t*)out = SpookyHash::Hash32(key, len, seed); 5 | } 6 | 7 | void SpookyHash64_test(const void *key, int len, uint32_t seed, void *out) { 8 | *(uint64_t*)out = SpookyHash::Hash64(key, len, seed); 9 | } 10 | 11 | void SpookyHash128_test(const void *key, int len, uint32_t seed, void *out) { 12 | uint64_t h1 = seed, h2 = seed; 13 | SpookyHash::Hash128(key, len, &h1, &h2); 14 | ((uint64_t*)out)[0] = h1; 15 | ((uint64_t*)out)[1] = h2; 16 | } 17 | -------------------------------------------------------------------------------- /deps/smhasher/sha1.h: -------------------------------------------------------------------------------- 1 | /* public api for steve reid's public domain SHA-1 implementation */ 2 | /* this file is in the public domain */ 3 | 4 | #pragma once 5 | 6 | #include "Platform.h" 7 | 8 | struct SHA1_CTX 9 | { 10 | uint32_t state[5]; 11 | uint32_t count[2]; 12 | uint8_t buffer[64]; 13 | }; 14 | 15 | #define SHA1_DIGEST_SIZE 20 16 | 17 | void SHA1_Init(SHA1_CTX* context); 18 | void SHA1_Update(SHA1_CTX* context, const uint8_t* data, const size_t len); 19 | void SHA1_Final(SHA1_CTX* context, uint8_t digest[SHA1_DIGEST_SIZE]); 20 | 21 | void sha1_32a ( const void * key, int len, uint32_t seed, void * out ); -------------------------------------------------------------------------------- /deps/yajl/.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | Makefile 3 | /build/ 4 | -------------------------------------------------------------------------------- /deps/yajl/BUILDING: -------------------------------------------------------------------------------- 1 | Short story (If you already have ruby and cmake): 2 | 3 | ./configure && make install 4 | 5 | When things go wrong: 6 | 7 | attain CMake (http://www.cmake.org) and ruby (http://ruby-lang.org) and 8 | try again. 9 | 10 | OR, attain CMake and build by hand: 11 | 12 | 1. mkdir build 13 | 2. cd build 14 | 3. cmake .. 15 | 4. make 16 | 5. build output left in yajl-X.Y.Z 17 | 18 | NOTE: for 64-bit systems where lib64 is used you can pass the cmake 19 | variable LIB_SUFFIX to cause installation into the system's 'lib64' 20 | directory. 21 | 22 | best, 23 | lloyd 24 | -------------------------------------------------------------------------------- /deps/yajl/BUILDING.win32: -------------------------------------------------------------------------------- 1 | YAJL has been successfully built using Visual Studio 8. CMake, a 2 | build file generator, is used to build the software. CMake supports 3 | several different build environments, so you may either build YAJL 4 | using the IDE via the following steps: 5 | 6 | 1. acquire cmake (http://www.cmake.org) 7 | 2. mkdir build 8 | 3. cd build 9 | 4. cmake .. 10 | 5. devenv YetAnotherJSONParser.sln /project ALL_BUILD /build Release 11 | 6. build output is left in build/yajl-X.Y.Z 12 | 13 | Or you can build from the command line using nmake: 14 | 15 | 1. Click Start > Programs > Microsoft Visual Studio > Visual Studio 16 | Tools > Visual Studio Command Prompt -- for your version of Visual 17 | Studio, which will open a command prompt. You may verify that the 18 | compiler is in your path by typing "cl /?" at the prompt. 19 | 2. cd C:\path\to\yajl\source\ 20 | 3. mkdir build 21 | 4. cd build 22 | 5. cmake -G"NMake Makefiles" -DCMAKE_BUILD_TYPE=Release .. 23 | 6. nmake 24 | 7. nmake install 25 | 26 | Earlier versions of visual studio and other build generators haven't 27 | been thoroughly tested, but should work without any major issues. 28 | -------------------------------------------------------------------------------- /deps/yajl/COPYING: -------------------------------------------------------------------------------- 1 | Copyright (c) 2007-2014, Lloyd Hilaiel 2 | 3 | Permission to use, copy, modify, and/or distribute this software for any 4 | purpose with or without fee is hereby granted, provided that the above 5 | copyright notice and this permission notice appear in all copies. 6 | 7 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | -------------------------------------------------------------------------------- /deps/yajl/TODO: -------------------------------------------------------------------------------- 1 | * add a test for 0x1F bug 2 | * numeric overflow in integers and double 3 | * line and char offsets in the lexer and in error messages 4 | * testing: 5 | a. the permuter 6 | b. some performance comparison against json_checker. 7 | * investigate pull instead of push parsing 8 | * Handle memory allocation failures gracefully 9 | * cygwin/msys support on win32 10 | -------------------------------------------------------------------------------- /deps/yajl/YAJLDoc.cmake: -------------------------------------------------------------------------------- 1 | FIND_PROGRAM(doxygenPath doxygen) 2 | 3 | IF (doxygenPath) 4 | SET (YAJL_VERSION ${YAJL_MAJOR}.${YAJL_MINOR}.${YAJL_MICRO}) 5 | SET(yajlDirName yajl-${YAJL_VERSION}) 6 | SET(docPath 7 | "${CMAKE_CURRENT_BINARY_DIR}/${yajlDirName}/share/doc/${yajlDirName}") 8 | MESSAGE("** using doxygen at: ${doxygenPath}") 9 | MESSAGE("** documentation output to: ${docPath}") 10 | 11 | CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/src/YAJL.dxy 12 | ${CMAKE_CURRENT_BINARY_DIR}/YAJL.dxy @ONLY) 13 | 14 | FILE(MAKE_DIRECTORY "${docPath}") 15 | 16 | ADD_CUSTOM_TARGET(doc 17 | ${doxygenPath} YAJL.dxy 18 | WORKING_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}) 19 | 20 | ELSE (doxygenPath) 21 | MESSAGE("!! doxygen not found, not generating documentation") 22 | ADD_CUSTOM_TARGET( 23 | doc 24 | echo doxygen not installed, not generating documentation 25 | ) 26 | ENDIF (doxygenPath) 27 | -------------------------------------------------------------------------------- /deps/yajl/example/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | SET (SRCS parse_config.c) 16 | 17 | # use the library we build, duh. 18 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include) 19 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib) 20 | 21 | ADD_EXECUTABLE(parse_config ${SRCS}) 22 | 23 | TARGET_LINK_LIBRARIES(parse_config yajl_s) 24 | -------------------------------------------------------------------------------- /deps/yajl/example/README.md: -------------------------------------------------------------------------------- 1 | This directory holds an example of how one might use yajl in the 2 | simplest possible way, to do something like parse and extract values 3 | from a configuration file. 4 | 5 | Note that use of the yajl_tree.h utility is completely optional, and 6 | yajl_parse.h offers a lower level stream parsing API that is more 7 | efficient and flexible at the cost of some complexity. 8 | -------------------------------------------------------------------------------- /deps/yajl/perf/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | SET (SRCS perftest.c documents.c documents.h) 16 | 17 | # use the library we build, duh. 18 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include) 19 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib) 20 | 21 | ADD_EXECUTABLE(perftest ${SRCS}) 22 | 23 | TARGET_LINK_LIBRARIES(perftest yajl_s) 24 | -------------------------------------------------------------------------------- /deps/yajl/perf/documents.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2007-2014, Lloyd Hilaiel 3 | * 4 | * Permission to use, copy, modify, and/or distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | #ifndef __DOCUMENTS_H__ 18 | #define __DOCUMENTS_H__ 19 | 20 | /* a header that provides access to several json documents broken into chunks of 21 | * less than 4k, cause C99 says that's what we should do and YAJL likes streams */ 22 | 23 | extern const char ** g_documents[]; 24 | int num_docs(void); 25 | const char ** get_doc(int i); 26 | unsigned int doc_size(int i); 27 | 28 | #endif 29 | -------------------------------------------------------------------------------- /deps/yajl/reformatter/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | # set up a paths 16 | SET (binDir ${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/bin) 17 | 18 | # create a directories 19 | FILE(MAKE_DIRECTORY ${binDir}) 20 | 21 | SET (SRCS json_reformat.c) 22 | 23 | # use the library we build, duh. 24 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include) 25 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib) 26 | 27 | ADD_EXECUTABLE(json_reformat ${SRCS}) 28 | 29 | TARGET_LINK_LIBRARIES(json_reformat yajl_s) 30 | 31 | # In some environments, we must explicitly link libm (like qnx, 32 | # thanks @shahbag) 33 | IF (NOT WIN32) 34 | TARGET_LINK_LIBRARIES(json_reformat m) 35 | ENDIF (NOT WIN32) 36 | 37 | # copy the binary into the output directory 38 | GET_TARGET_PROPERTY(binPath json_reformat LOCATION) 39 | 40 | ADD_CUSTOM_COMMAND(TARGET json_reformat POST_BUILD 41 | COMMAND ${CMAKE_COMMAND} -E copy_if_different ${binPath} ${binDir}) 42 | 43 | INSTALL(TARGETS json_reformat RUNTIME DESTINATION bin) 44 | -------------------------------------------------------------------------------- /deps/yajl/src/api/yajl_version.h.cmake: -------------------------------------------------------------------------------- 1 | #ifndef YAJL_VERSION_H_ 2 | #define YAJL_VERSION_H_ 3 | 4 | #include 5 | 6 | #define YAJL_MAJOR ${YAJL_MAJOR} 7 | #define YAJL_MINOR ${YAJL_MINOR} 8 | #define YAJL_MICRO ${YAJL_MICRO} 9 | 10 | #define YAJL_VERSION ((YAJL_MAJOR * 10000) + (YAJL_MINOR * 100) + YAJL_MICRO) 11 | 12 | #ifdef __cplusplus 13 | extern "C" { 14 | #endif 15 | 16 | extern int YAJL_API yajl_version(void); 17 | 18 | #ifdef __cplusplus 19 | } 20 | #endif 21 | 22 | #endif /* YAJL_VERSION_H_ */ 23 | 24 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl: -------------------------------------------------------------------------------- 1 | /** 2 | \example reformatter/json_reformat.c 3 | \example example/parse_config.c 4 | */ 5 | 6 | /*! 7 | \mainpage Yet Another JSON Library (YAJL) 8 | \author Lloyd Hilaiel 9 | \date 2007-2014 10 | 11 | Yet Another JSON Library (YAJL) is a small event-driven (SAX-style) 12 | JSON parser written in ANSI C, and a small validating JSON 13 | generator. YAJL is released under the permissive ISC license. 14 | 15 | \section features Features 16 | 17 | -# Stream (incremental) parsing and generation of JSON 18 | -# ANSI C 19 | -# Human readable error messages with context 20 | -# tiny 21 | -# event driven 22 | -# support for generating "beautified" JSON 23 | -# includes 24 | It also includes a small simplified tree interface for 25 | simplified parsing and extraction of data from smallish JSON documents. 26 | 27 | \section usage Usage 28 | 29 | See
json_reformat.c for a complete example of stream based parsing 30 | and generation of JSON. See parse_config.c for an example of the 31 | simplified tree interface. 32 | 33 | */ 34 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl.pc.cmake: -------------------------------------------------------------------------------- 1 | prefix=${CMAKE_INSTALL_PREFIX} 2 | libdir=${dollar}{prefix}/lib${LIB_SUFFIX} 3 | includedir=${dollar}{prefix}/include/yajl 4 | 5 | Name: Yet Another JSON Library 6 | Description: A Portable JSON parsing and serialization library in ANSI C 7 | Version: ${YAJL_MAJOR}.${YAJL_MINOR}.${YAJL_MICRO} 8 | Cflags: -I${dollar}{includedir} 9 | Libs: -L${dollar}{libdir} -lyajl 10 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl_alloc.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2007-2014, Lloyd Hilaiel 3 | * 4 | * Permission to use, copy, modify, and/or distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | /** 18 | * \file yajl_alloc.h 19 | * default memory allocation routines for yajl which use malloc/realloc and 20 | * free 21 | */ 22 | 23 | #include "yajl_alloc.h" 24 | #include 25 | 26 | static void * yajl_internal_malloc(void *ctx, size_t sz) 27 | { 28 | (void)ctx; 29 | return malloc(sz); 30 | } 31 | 32 | static void * yajl_internal_realloc(void *ctx, void * previous, 33 | size_t sz) 34 | { 35 | (void)ctx; 36 | return realloc(previous, sz); 37 | } 38 | 39 | static void yajl_internal_free(void *ctx, void * ptr) 40 | { 41 | (void)ctx; 42 | free(ptr); 43 | } 44 | 45 | void yajl_set_default_alloc_funcs(yajl_alloc_funcs * yaf) 46 | { 47 | yaf->malloc = yajl_internal_malloc; 48 | yaf->free = yajl_internal_free; 49 | yaf->realloc = yajl_internal_realloc; 50 | yaf->ctx = NULL; 51 | } 52 | 53 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl_alloc.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2007-2014, Lloyd Hilaiel 3 | * 4 | * Permission to use, copy, modify, and/or distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | /** 18 | * \file yajl_alloc.h 19 | * default memory allocation routines for yajl which use malloc/realloc and 20 | * free 21 | */ 22 | 23 | #ifndef __YAJL_ALLOC_H__ 24 | #define __YAJL_ALLOC_H__ 25 | 26 | #include "api/yajl_common.h" 27 | 28 | #define YA_MALLOC(afs, sz) (afs)->malloc((afs)->ctx, (sz)) 29 | #define YA_FREE(afs, ptr) (afs)->free((afs)->ctx, (ptr)) 30 | #define YA_REALLOC(afs, ptr, sz) (afs)->realloc((afs)->ctx, (ptr), (sz)) 31 | 32 | void yajl_set_default_alloc_funcs(yajl_alloc_funcs * yaf); 33 | 34 | #endif 35 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl_encode.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2007-2014, Lloyd Hilaiel 3 | * 4 | * Permission to use, copy, modify, and/or distribute this software for any 5 | * purpose with or without fee is hereby granted, provided that the above 6 | * copyright notice and this permission notice appear in all copies. 7 | * 8 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 13 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 14 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 | */ 16 | 17 | #ifndef __YAJL_ENCODE_H__ 18 | #define __YAJL_ENCODE_H__ 19 | 20 | #include "yajl_buf.h" 21 | #include "api/yajl_gen.h" 22 | 23 | void yajl_string_encode(const yajl_print_t printer, 24 | void * ctx, 25 | const unsigned char * str, 26 | size_t length, 27 | int escape_solidus); 28 | 29 | void yajl_string_decode(yajl_buf buf, const unsigned char * str, 30 | size_t length); 31 | 32 | int yajl_string_validate_utf8(const unsigned char * s, size_t len); 33 | 34 | #endif 35 | -------------------------------------------------------------------------------- /deps/yajl/src/yajl_version.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int yajl_version(void) 4 | { 5 | return YAJL_VERSION; 6 | } 7 | 8 | -------------------------------------------------------------------------------- /deps/yajl/test/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | ADD_SUBDIRECTORY(parsing) 16 | ADD_SUBDIRECTORY(api) 17 | -------------------------------------------------------------------------------- /deps/yajl/test/api/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | SET (TESTS gen-extra-close.c 16 | ) 17 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../../${YAJL_DIST_NAME}/include) 18 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../../${YAJL_DIST_NAME}/lib) 19 | 20 | # for each test, we'll create a target, and make the api-tests target depend on it 21 | FOREACH (test ${TESTS}) 22 | GET_FILENAME_COMPONENT(testProg ${test} NAME_WE) 23 | ADD_EXECUTABLE(${testProg} ${test}) 24 | TARGET_LINK_LIBRARIES(${testProg} yajl) 25 | ENDFOREACH() 26 | -------------------------------------------------------------------------------- /deps/yajl/test/api/gen-extra-close.c: -------------------------------------------------------------------------------- 1 | /* ensure that if we try to generate an extra closing brace 2 | * we get the expected error */ 3 | 4 | #include 5 | #include 6 | 7 | #define CHK(x) if (x != yajl_gen_status_ok) return 1; 8 | 9 | int main(void) { 10 | yajl_gen yg; 11 | yajl_gen_status s; 12 | 13 | yg = yajl_gen_alloc(NULL); 14 | CHK(yajl_gen_map_open(yg)); 15 | CHK(yajl_gen_map_close(yg)); 16 | s = yajl_gen_map_close(yg); 17 | 18 | return (yajl_gen_generation_complete == s); 19 | } 20 | -------------------------------------------------------------------------------- /deps/yajl/test/api/run_tests.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | echo Running api tests: 4 | 5 | tests=0 6 | passed=0 7 | 8 | for file in `ls`; do 9 | [ ! -x $file -o -d $file ] && continue 10 | tests=`expr 1 + $tests` 11 | printf " test(%s): " $file 12 | ./$file 13 | if [ $? ]; then 14 | passed=`expr 1 + $passed` 15 | echo 'SUCCESS' 16 | else 17 | echo 'FAILURE' 18 | fi 19 | done 20 | 21 | echo "$passed/$tests tests successful" 22 | 23 | exit 0 24 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | SET (SRCS yajl_test.c) 16 | 17 | # use the library we build, duh. 18 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../../${YAJL_DIST_NAME}/include) 19 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../../${YAJL_DIST_NAME}/lib) 20 | 21 | ADD_EXECUTABLE(yajl_test ${SRCS}) 22 | 23 | TARGET_LINK_LIBRARIES(yajl_test yajl_s) 24 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ac_difficult_json_c_test_case_with_comments.json: -------------------------------------------------------------------------------- 1 | { "glossary": { /* you */ "title": /**/ "example glossary", /*should*/"GlossDiv": { "title": /*never*/"S", /*ever*/"GlossList": [ { "ID": "SGML", "SortAs": "SGML", "GlossTerm": "Standard Generalized Markup Language", "Acronym": "SGML", "Abbrev": "ISO 8879:1986", "GlossDef": "A meta-markup language, used to create markup languages such as DocBook.", /*see*/"GlossSeeAlso"/*this*/:/*coming*/[/*out*/"GML"/*of*/,/*the*/"XML"/*parser!*/, "markup"] /*hey*/}/*ho*/]/*hey*/}/*ho*/} } // and the parser won't even get this far, so chill. /* hah! 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ac_difficult_json_c_test_case_with_comments.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'glossary' 3 | map open '{' 4 | key: 'title' 5 | string: 'example glossary' 6 | key: 'GlossDiv' 7 | map open '{' 8 | key: 'title' 9 | string: 'S' 10 | key: 'GlossList' 11 | array open '[' 12 | map open '{' 13 | key: 'ID' 14 | string: 'SGML' 15 | key: 'SortAs' 16 | string: 'SGML' 17 | key: 'GlossTerm' 18 | string: 'Standard Generalized Markup Language' 19 | key: 'Acronym' 20 | string: 'SGML' 21 | key: 'Abbrev' 22 | string: 'ISO 8879:1986' 23 | key: 'GlossDef' 24 | string: 'A meta-markup language, used to create markup languages such as DocBook.' 25 | key: 'GlossSeeAlso' 26 | array open '[' 27 | string: 'GML' 28 | string: 'XML' 29 | string: 'markup' 30 | array close ']' 31 | map close '}' 32 | array close ']' 33 | map close '}' 34 | map close '}' 35 | map close '}' 36 | memory leaks: 0 37 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ac_simple_with_comments.json: -------------------------------------------------------------------------------- 1 | { 2 | "this": "is", // ignore this 3 | "really": "simple", 4 | /* ignore 5 | this 6 | too * / 7 | ** // 8 | (/ 9 | ******/ 10 | "json": "right?" 11 | } 12 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ac_simple_with_comments.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'this' 3 | string: 'is' 4 | key: 'really' 5 | string: 'simple' 6 | key: 'json' 7 | string: 'right?' 8 | map close '}' 9 | memory leaks: 0 10 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_false_then_garbage.json: -------------------------------------------------------------------------------- 1 | falsex -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_false_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | bool: false 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_null_then_garbage.json: -------------------------------------------------------------------------------- 1 | nullx 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_null_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | null 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_true_then_garbage.json: -------------------------------------------------------------------------------- 1 | truex -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ag_true_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | bool: true 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_eof.json: -------------------------------------------------------------------------------- 1 | { "123": 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_eof.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: '123' 3 | parse error: premature EOF 4 | memory leaks: 0 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_integers.json: -------------------------------------------------------------------------------- 1 | 1221 21 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_integers.json.gold: -------------------------------------------------------------------------------- 1 | integer: 1221 2 | integer: 21 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_multiple.json: -------------------------------------------------------------------------------- 1 | 2 | {} 3 | {} 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_multiple.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | map close '}' 3 | map open '{' 4 | map close '}' 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_stuff.json: -------------------------------------------------------------------------------- 1 | {} 2 | [] 3 | [] 4 | "sdfasd" 5 | 123 6 | { "123" : 123 } 7 | 3.1e124 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/am_stuff.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | map close '}' 3 | array open '[' 4 | array close ']' 5 | array open '[' 6 | array close ']' 7 | string: 'sdfasd' 8 | integer: 123 9 | map open '{' 10 | key: '123' 11 | integer: 123 12 | map close '}' 13 | double: 3.1e+124 14 | memory leaks: 0 15 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_array_open.json: -------------------------------------------------------------------------------- 1 | [ 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_array_open.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_eof_str.json: -------------------------------------------------------------------------------- 1 | "abc -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_eof_str.json.gold: -------------------------------------------------------------------------------- 1 | memory leaks: 0 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_map_open.json: -------------------------------------------------------------------------------- 1 | { 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_map_open.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_partial_ok.json: -------------------------------------------------------------------------------- 1 | [ "foo", "bar" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/ap_partial_ok.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'foo' 3 | string: 'bar' 4 | memory leaks: 0 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/array.json: -------------------------------------------------------------------------------- 1 | ["foo", 2 | "bar", "baz", 3 | true,false,null,{"key":"value"}, 4 | [null,null,null,[]], 5 | "\n\r\\" 6 | ] 7 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/array.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'foo' 3 | string: 'bar' 4 | string: 'baz' 5 | bool: true 6 | bool: false 7 | null 8 | map open '{' 9 | key: 'key' 10 | string: 'value' 11 | map close '}' 12 | array open '[' 13 | null 14 | null 15 | null 16 | array open '[' 17 | array close ']' 18 | array close ']' 19 | string: ' 20 | \' 21 | array close ']' 22 | memory leaks: 0 23 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/array_close.json: -------------------------------------------------------------------------------- 1 | ] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/array_close.json.gold: -------------------------------------------------------------------------------- 1 | parse error: unallowed token at this point in JSON text 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/bignums.json: -------------------------------------------------------------------------------- 1 | [ 9223372036854775807, -9223372036854775807 ] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/bignums.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | integer: 9223372036854775807 3 | integer: -9223372036854775807 4 | array close ']' 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/bogus_char.json: -------------------------------------------------------------------------------- 1 | ["this","is","what","should","be", 2 | "a happy bit of json", 3 | "but someone, misspelled \"true\"", ture, 4 | "who says JSON is easy for humans to generate?"] 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/bogus_char.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'this' 3 | string: 'is' 4 | string: 'what' 5 | string: 'should' 6 | string: 'be' 7 | string: 'a happy bit of json' 8 | string: 'but someone, misspelled "true"' 9 | lexical error: invalid string in json text. 10 | memory leaks: 0 11 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/codepoints_from_unicode_org.json: -------------------------------------------------------------------------------- 1 | "\u004d\u0430\u4e8c\ud800\udf02" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/codepoints_from_unicode_org.json.gold: -------------------------------------------------------------------------------- 1 | string: 'Mа二𐌂' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/difficult_json_c_test_case.json: -------------------------------------------------------------------------------- 1 | { "glossary": { "title": "example glossary", "GlossDiv": { "title": "S", "GlossList": [ { "ID": "SGML", "SortAs": "SGML", "GlossTerm": "Standard Generalized Markup Language", "Acronym": "SGML", "Abbrev": "ISO 8879:1986", "GlossDef": "A meta-markup language, used to create markup languages such as DocBook.", "GlossSeeAlso": ["GML", "XML", "markup"] } ] } } } 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/difficult_json_c_test_case.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'glossary' 3 | map open '{' 4 | key: 'title' 5 | string: 'example glossary' 6 | key: 'GlossDiv' 7 | map open '{' 8 | key: 'title' 9 | string: 'S' 10 | key: 'GlossList' 11 | array open '[' 12 | map open '{' 13 | key: 'ID' 14 | string: 'SGML' 15 | key: 'SortAs' 16 | string: 'SGML' 17 | key: 'GlossTerm' 18 | string: 'Standard Generalized Markup Language' 19 | key: 'Acronym' 20 | string: 'SGML' 21 | key: 'Abbrev' 22 | string: 'ISO 8879:1986' 23 | key: 'GlossDef' 24 | string: 'A meta-markup language, used to create markup languages such as DocBook.' 25 | key: 'GlossSeeAlso' 26 | array open '[' 27 | string: 'GML' 28 | string: 'XML' 29 | string: 'markup' 30 | array close ']' 31 | map close '}' 32 | array close ']' 33 | map close '}' 34 | map close '}' 35 | map close '}' 36 | memory leaks: 0 37 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/doubles.json: -------------------------------------------------------------------------------- 1 | [ 0.1e2, 1e1, 3.141569, 10000000000000e-10] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/doubles.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | double: 10 3 | double: 10 4 | double: 3.14157 5 | double: 1000 6 | array close ']' 7 | memory leaks: 0 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/doubles_in_array.json: -------------------------------------------------------------------------------- 1 | [0.00011999999999999999, 6E-06, 6E-06, 1E-06, 1E-06] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/doubles_in_array.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | double: 0.00012 3 | double: 6e-06 4 | double: 6e-06 5 | double: 1e-06 6 | double: 1e-06 7 | array close ']' 8 | memory leaks: 0 9 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/empty_array.json: -------------------------------------------------------------------------------- 1 | [] -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/empty_array.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | array close ']' 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/empty_string.json: -------------------------------------------------------------------------------- 1 | "" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/empty_string.json.gold: -------------------------------------------------------------------------------- 1 | string: '' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/escaped_bulgarian.json: -------------------------------------------------------------------------------- 1 | ["\u0414\u0430", 2 | "\u041c\u0443", 3 | "\u0415\u0431\u0430", 4 | "\u041c\u0430\u0439\u043a\u0430\u0442\u0430"] 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/escaped_bulgarian.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'Да' 3 | string: 'Му' 4 | string: 'Еба' 5 | string: 'Майката' 6 | array close ']' 7 | memory leaks: 0 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/escaped_foobar.json: -------------------------------------------------------------------------------- 1 | "\u0066\u006f\u006f\u0062\u0061\u0072" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/escaped_foobar.json.gold: -------------------------------------------------------------------------------- 1 | string: 'foobar' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/false.json: -------------------------------------------------------------------------------- 1 | false 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/false.json.gold: -------------------------------------------------------------------------------- 1 | bool: false 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_false_then_garbage.json: -------------------------------------------------------------------------------- 1 | falsex -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_false_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | bool: false 2 | parse error: trailing garbage 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_issue_7.json: -------------------------------------------------------------------------------- 1 | 2009-10-20@20:38:21.539575 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_issue_7.json.gold: -------------------------------------------------------------------------------- 1 | integer: 2009 2 | parse error: trailing garbage 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_null_then_garbage.json: -------------------------------------------------------------------------------- 1 | nullx 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_null_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | null 2 | parse error: trailing garbage 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_true_then_garbage.json: -------------------------------------------------------------------------------- 1 | truex 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/fg_true_then_garbage.json.gold: -------------------------------------------------------------------------------- 1 | bool: true 2 | parse error: trailing garbage 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/four_byte_utf8.json: -------------------------------------------------------------------------------- 1 | { "U+10ABCD": "􊯍" } 2 | 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/four_byte_utf8.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'U+10ABCD' 3 | string: '􊯍' 4 | map close '}' 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/high_overflow.json: -------------------------------------------------------------------------------- 1 | 9223372036854775808 -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/high_overflow.json.gold: -------------------------------------------------------------------------------- 1 | parse error: integer overflow 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/integers.json: -------------------------------------------------------------------------------- 1 | [ 1,2,3,4,5,6,7, 2 | 123456789 , -123456789, 3 | 2147483647, -2147483647 ] 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/integers.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | integer: 1 3 | integer: 2 4 | integer: 3 5 | integer: 4 6 | integer: 5 7 | integer: 6 8 | integer: 7 9 | integer: 123456789 10 | integer: -123456789 11 | integer: 2147483647 12 | integer: -2147483647 13 | array close ']' 14 | memory leaks: 0 15 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/invalid_utf8.json: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/deps/yajl/test/parsing/cases/invalid_utf8.json -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/invalid_utf8.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | lexical error: invalid bytes in UTF8 string. 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/isolated_surrogate_marker.json: -------------------------------------------------------------------------------- 1 | "\ud800" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/isolated_surrogate_marker.json.gold: -------------------------------------------------------------------------------- 1 | string: '?' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/leading_zero_in_number.json: -------------------------------------------------------------------------------- 1 | { "bad thing": 01 } 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/leading_zero_in_number.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'bad thing' 3 | integer: 0 4 | parse error: after key and value, inside map, I expect ',' or '}' 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/lonely_minus_sign.json: -------------------------------------------------------------------------------- 1 | [ 2 | "foo", true, 3 | true, "blue", 4 | "baby where are you?", "oh boo hoo!", 5 | - 6 | ] 7 | 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/lonely_minus_sign.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'foo' 3 | bool: true 4 | bool: true 5 | string: 'blue' 6 | string: 'baby where are you?' 7 | string: 'oh boo hoo!' 8 | lexical error: malformed number, a digit is required after the minus sign. 9 | memory leaks: 0 10 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/lonely_number.json: -------------------------------------------------------------------------------- 1 | 123456789 -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/lonely_number.json.gold: -------------------------------------------------------------------------------- 1 | integer: 123456789 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/low_overflow.json: -------------------------------------------------------------------------------- 1 | -9223372036854775808 -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/low_overflow.json.gold: -------------------------------------------------------------------------------- 1 | parse error: integer overflow 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/map_close.json: -------------------------------------------------------------------------------- 1 | } 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/map_close.json.gold: -------------------------------------------------------------------------------- 1 | parse error: unallowed token at this point in JSON text 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/missing_integer_after_decimal_point.json: -------------------------------------------------------------------------------- 1 | 10.e2 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/missing_integer_after_decimal_point.json.gold: -------------------------------------------------------------------------------- 1 | lexical error: malformed number, a digit is required after the decimal point. 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/missing_integer_after_exponent.json: -------------------------------------------------------------------------------- 1 | 10e 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/missing_integer_after_exponent.json.gold: -------------------------------------------------------------------------------- 1 | lexical error: malformed number, a digit is required after the exponent. 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/multiple.json: -------------------------------------------------------------------------------- 1 | 2 | {} 3 | {} 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/multiple.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | map close '}' 3 | parse error: trailing garbage 4 | memory leaks: 0 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/non_utf8_char_in_string.json: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/deps/yajl/test/parsing/cases/non_utf8_char_in_string.json -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/non_utf8_char_in_string.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'CoreletAPIVersion' 3 | integer: 2 4 | key: 'CoreletType' 5 | string: 'standalone' 6 | key: 'documentation' 7 | lexical error: invalid bytes in UTF8 string. 8 | memory leaks: 0 9 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/np_partial_bad.json: -------------------------------------------------------------------------------- 1 | [ "foo", "bar" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/np_partial_bad.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'foo' 3 | string: 'bar' 4 | parse error: premature EOF 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/null.json: -------------------------------------------------------------------------------- 1 | null 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/null.json.gold: -------------------------------------------------------------------------------- 1 | null 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/nulls_and_bools.json: -------------------------------------------------------------------------------- 1 | { 2 | "boolean, true": true, 3 | "boolean, false": false, 4 | "null": null 5 | } 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/nulls_and_bools.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'boolean, true' 3 | bool: true 4 | key: 'boolean, false' 5 | bool: false 6 | key: 'null' 7 | null 8 | map close '}' 9 | memory leaks: 0 10 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/simple.json: -------------------------------------------------------------------------------- 1 | { 2 | "this": "is", 3 | "really": "simple", 4 | "json": "right?" 5 | } 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/simple.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'this' 3 | string: 'is' 4 | key: 'really' 5 | string: 'simple' 6 | key: 'json' 7 | string: 'right?' 8 | map close '}' 9 | memory leaks: 0 10 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/simple_with_comments.json: -------------------------------------------------------------------------------- 1 | { 2 | "this": "is", // ignore this 3 | "really": "simple", 4 | /* ignore 5 | this 6 | too * / 7 | ** // 8 | (/ 9 | ******/ 10 | "json": "right?" 11 | } 12 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/simple_with_comments.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'this' 3 | string: 'is' 4 | lexical error: probable comment found in input text, comments are not enabled. 5 | memory leaks: 0 6 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_invalid_escape.json: -------------------------------------------------------------------------------- 1 | ["\n foo \/ bar \r\f\\\uffff\t\b\"\\ and you can't escape thi\s"] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_invalid_escape.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | lexical error: inside a string, '\' occurs before a character which it may not. 3 | memory leaks: 0 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_invalid_hex_char.json: -------------------------------------------------------------------------------- 1 | "foo foo, blah blah \u0123 \u4567 \u89ab \uc/ef \uABCD \uEFFE bar baz bing" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_invalid_hex_char.json.gold: -------------------------------------------------------------------------------- 1 | lexical error: invalid (non-hex) character occurs after '\u' inside string. 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_with_escapes.json: -------------------------------------------------------------------------------- 1 | ["\n foo \/ bar \r\f\\\uffff\t\b\"\\", 2 | "\"and this string has an escape at the beginning", 3 | "and this string has no escapes" ] 4 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_with_escapes.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: ' 3 | foo / bar \￿ "\' 4 | string: '"and this string has an escape at the beginning' 5 | string: 'and this string has no escapes' 6 | array close ']' 7 | memory leaks: 0 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_with_invalid_newline.json: -------------------------------------------------------------------------------- 1 | "la di dah. this is a string, and I can do this, \n, but not this 2 | " 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/string_with_invalid_newline.json.gold: -------------------------------------------------------------------------------- 1 | lexical error: invalid character inside string. 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/three_byte_utf8.json: -------------------------------------------------------------------------------- 1 | {"matzue": "松江", "asakusa": "浅草"} 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/three_byte_utf8.json.gold: -------------------------------------------------------------------------------- 1 | map open '{' 2 | key: 'matzue' 3 | string: '松江' 4 | key: 'asakusa' 5 | string: '浅草' 6 | map close '}' 7 | memory leaks: 0 8 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/true.json: -------------------------------------------------------------------------------- 1 | true 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/true.json.gold: -------------------------------------------------------------------------------- 1 | bool: true 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/unescaped_bulgarian.json: -------------------------------------------------------------------------------- 1 | ["Да Му Еба Майката"] 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/unescaped_bulgarian.json.gold: -------------------------------------------------------------------------------- 1 | array open '[' 2 | string: 'Да Му Еба Майката' 3 | array close ']' 4 | memory leaks: 0 5 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/zerobyte.json: -------------------------------------------------------------------------------- 1 | "\u0000" 2 | -------------------------------------------------------------------------------- /deps/yajl/test/parsing/cases/zerobyte.json.gold: -------------------------------------------------------------------------------- 1 | string: '' 2 | memory leaks: 0 3 | -------------------------------------------------------------------------------- /deps/yajl/verify/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | # Copyright (c) 2007-2014, Lloyd Hilaiel 2 | # 3 | # Permission to use, copy, modify, and/or distribute this software for any 4 | # purpose with or without fee is hereby granted, provided that the above 5 | # copyright notice and this permission notice appear in all copies. 6 | # 7 | # THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | # WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | # MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | # ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | # WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | # ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | # OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | 15 | # set up some paths 16 | SET (binDir ${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/bin) 17 | 18 | # create some directories 19 | FILE(MAKE_DIRECTORY ${binDir}) 20 | 21 | SET (SRCS json_verify.c) 22 | 23 | # use the library we build, duh. 24 | INCLUDE_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/include) 25 | LINK_DIRECTORIES(${CMAKE_CURRENT_BINARY_DIR}/../${YAJL_DIST_NAME}/lib) 26 | 27 | ADD_EXECUTABLE(json_verify ${SRCS}) 28 | 29 | TARGET_LINK_LIBRARIES(json_verify yajl_s) 30 | 31 | # copy in the binary 32 | GET_TARGET_PROPERTY(binPath json_verify LOCATION) 33 | 34 | ADD_CUSTOM_COMMAND(TARGET json_verify POST_BUILD 35 | COMMAND ${CMAKE_COMMAND} -E copy_if_different ${binPath} ${binDir}) 36 | 37 | INSTALL(TARGETS json_verify RUNTIME DESTINATION bin) 38 | -------------------------------------------------------------------------------- /res/blog/static/commonmark.min.js.gz: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/blog/static/commonmark.min.js.gz -------------------------------------------------------------------------------- /res/blog/static/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/blog/static/favicon.ico -------------------------------------------------------------------------------- /res/blog/static/file.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/blog/static/file.png -------------------------------------------------------------------------------- /res/blog/static/hash-handler.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | Hash Handler 4 | 5 | 6 |

Experimental hash: protocol handler.

7 | 8 |
    9 |
  • Firefox on Linux: works well 10 |
  • Firefox on OS X: only works from links within Firefox 11 |
  • Chrome: custom protocols must be prefixed with "web+" in a misguided attempt at security 12 |
  • Other configurations: not tested 13 |
14 | 15 |

Pending...

16 | 17 | 18 | 19 | 20 | 36 | 37 | -------------------------------------------------------------------------------- /res/blog/template/empty.html: -------------------------------------------------------------------------------- 1 |

(no preview)

2 | 3 | -------------------------------------------------------------------------------- /res/blog/template/entry-end.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /res/blog/template/entry-start.html: -------------------------------------------------------------------------------- 1 |
2 |
3 | [View] 4 | [Short] 5 | [Hash] 6 | [Raw] 7 |
8 |
9 | -------------------------------------------------------------------------------- /res/blog/template/footer.html: -------------------------------------------------------------------------------- 1 |
2 | Newest ‒ 3 | Newer ‒ 4 | Older ‒ 5 | Oldest 6 |
7 | 8 | -------------------------------------------------------------------------------- /res/blog/template/header.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | {{reponame}} 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 |
14 | Home ‒ 15 | {{account}} ‒ 16 | Compose ‒ 17 | Upload 18 |
19 |

{{reponame}}

20 |
21 |
22 |
23 | 31 |
32 | -------------------------------------------------------------------------------- /res/blog/template/login.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {{reponame}} login 4 | 5 | 39 | 40 |
53 | 54 | 55 | -------------------------------------------------------------------------------- /res/blog/template/noresults.html: -------------------------------------------------------------------------------- 1 |
2 |
3 |

No results

4 |

No files matching the specified query were found.

5 |
    6 |
  • Broaden the query by removing terms. 7 |
  • Remove sentence fragments like “what is…” or “how do I…”. 8 |
  • Make sure terms are spelled correctly. 9 |
10 |
11 |
12 | -------------------------------------------------------------------------------- /res/blog/template/notfound.html: -------------------------------------------------------------------------------- 1 |
2 |
3 |

Not found

4 |

No file with the requested hash could be found in this repository. The file might be part of a different repository or might not exist.

5 |
    6 |
  • The file might be private. 7 |
  • Check other repositories you have access to. 8 |
  • Check that the address was entered correctly. 9 |
  • Try a hash from a different algorithm (e.g. sha256). 10 |
11 |

If you have write access to this repository, you can add the file yourself or sync it from somewhere else.

12 |

If the file was deleted or taken down, you can set up a mirror to preserve files in the future.

13 |
14 |
15 | -------------------------------------------------------------------------------- /res/blog/template/preview.html: -------------------------------------------------------------------------------- 1 |
2 | 3 |
4 | 5 |
{{description}}
6 |
{{fileSize}}
7 | 8 |
9 |
10 |
11 | -------------------------------------------------------------------------------- /res/blog/template/rss/head.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | {{reponame}} 7 | . 8 | 9 | -------------------------------------------------------------------------------- /res/blog/template/rss/item-end.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /res/blog/template/rss/item-start.xml: -------------------------------------------------------------------------------- 1 | 2 | {{title}} 3 | {{queryURI}} 4 | {{description}} 5 | {{queryURI}} 6 | 7 | -------------------------------------------------------------------------------- /res/blog/template/rss/tail.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | -------------------------------------------------------------------------------- /res/blog/template/upload.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {{reponame}} upload 4 | 5 | 8 | 9 |
10 | 11 |
12 | 13 | 14 |
15 | 16 | -------------------------------------------------------------------------------- /res/experiments/2013-06-15 EFS submission.js: -------------------------------------------------------------------------------- 1 | function genHash(path, callback/* (err, hash) */) {} 2 | function genURNs(path, callback/* (err, URNs) */) {} 3 | function plainText(path, callback/* (err, str) */) {} 4 | function extractURIsByType(str) {} 5 | 6 | //function ancestors(URIs, callback/* (err, URIs) */) {} 7 | function descendants(hash, callback/* (err, URIs) */) {} 8 | function metaDescendants(hash, callback/* (err, URIs) */) {} 9 | 10 | function cacheAncestors(hash, callback/* (err) */) {} 11 | 12 | /// 13 | 14 | function Entry() {} 15 | Entry.prototype.textContent = ; 16 | Entry.prototype. 17 | 18 | Repo.prototype.addEntry = function(path) {}; 19 | 20 | /// 21 | 22 | function File(path) { 23 | var file = this; 24 | file.stream = null; 25 | file.URNs = null; 26 | file.hash = null; 27 | } 28 | File.prototype.load = function() { 29 | var file = this; 30 | file.stream = fs.createReadStream(path, {}); 31 | }; 32 | File.prototype.loadURNs = function() {}; 33 | 34 | 35 | Repo.prototype.addEntryFile = function(file, callback) {}; 36 | 37 | /// 38 | 39 | function generateURNs(path, callback/* (err, URNs, hash) */) {} 40 | function loadPlainText(path, callback/* (err, str) */) {} 41 | function parseURIs(str) {} 42 | function trackLinks(hash, URIs, callback/* (err) */) {} 43 | 44 | 45 | /* 46 | 47 | Search 48 | - Do we need to be able to show ancestors? Descendants? When? 49 | - When searching for a keyword, should descendants/ancestors be visible? 50 | - What kind of options do we want? What kind of interface should they have? 51 | 52 | */ 53 | 54 | 55 | 56 | 57 | -------------------------------------------------------------------------------- /res/experiments/2013-07-01 EarthFS Redesign.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | 4 | /* 5 | 6 | repo.efs/ 7 | 8 | 9 | /branches/ 10 | /remotes/ 11 | 12 | 13 | /config/ 14 | 15 | targets (branches) 16 | sources (authors?) 17 | remotes 18 | 19 | Branches need to perform lookups in two ways: 20 | - As ordered lists/ranges 21 | - Random access, to reject duplicates 22 | 23 | The ordered list can be satisfied by a plain text file with one SHA1 per line. 24 | 25 | 26 | 27 | */ 28 | 29 | 30 | -------------------------------------------------------------------------------- /res/experiments/2013-08-27 EarthFS Draft.odt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2013-08-27 EarthFS Draft.odt -------------------------------------------------------------------------------- /res/experiments/2013-09-12 EarthFS Draft 2.odt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2013-09-12 EarthFS Draft 2.odt -------------------------------------------------------------------------------- /res/experiments/2013-09-18-test-fibers.js: -------------------------------------------------------------------------------- 1 | var Fiber = require('/home/ben/Code/earthd/node_modules/fibers'); 2 | 3 | var fn = Fiber(function() { 4 | console.log('async work here...'); 5 | Fiber.yield(); 6 | console.log('still working...'); 7 | Fiber.yield(); 8 | console.log('just a little bit more...'); 9 | Fiber.yield(); 10 | // try { 11 | throw new Error('oh crap!'); 12 | // } catch(e) {} 13 | }); 14 | 15 | //try { 16 | while (true) { 17 | fn.run(); 18 | } 19 | //} catch(e) { 20 | // console.log('safely caught that error!'); 21 | // console.log(e.stack); 22 | //} 23 | console.log('done!'); 24 | 25 | -------------------------------------------------------------------------------- /res/experiments/2013-09-20-efs-queries.sql: -------------------------------------------------------------------------------- 1 | SELECT f."fileID" 2 | FROM "files" AS f 3 | LEFT JOIN "fileHashes" AS fh ON (fh."fileID" = f."fileID") 4 | LEFT JOIN "hashes" AS h ON (h."hashID" = fh."hashID") 5 | LEFT JOIN "fileIndexes" AS i ON (i."fileID" = f."fileID") 6 | LEFT JOIN "fileLinks" AS l ON (l."fileID" = f."fileID") 7 | LEFT JOIN "submissions" AS s ON (s."fileID" = f."fileID") 8 | LEFT JOIN "targets" AS t ON (t."submissionID" = s."submissionID") 9 | WHERE 10 | 11 | --query.Source 12 | (s."userID" = $x) 13 | (f."fileID" IN (SELECT "fileID" FROM "submissions" WHERE "userID" = $x)) 14 | 15 | --query.Target 16 | (t."userID" = $x) 17 | (f."fileID" IN (SELECT s."fileID" FROM "submissions" AS s INNER JOIN "targets" AS t ON (t."submissionID" = s."submissionID") WHERE t."userID" = $x)) 18 | 19 | --query.Terms 20 | (plainto_tsquery('english', $x) = ''::tsquery OR i."index" @@ plainto_tsquery('english', $x)) 21 | 22 | --query.LinksTo 23 | (l."normalizedURI" = $x) 24 | -- Add the files own hashes as `fileLinks` to itself. 25 | 26 | --query.All 27 | (x AND y AND z) 28 | 29 | --query.Any 30 | (x OR y OR z) 31 | 32 | ORDER BY f."fileID" ASC 33 | 34 | -------------------------------------------------------------------------------- /res/experiments/2013-09-20-node-fibers-error-test-case.js: -------------------------------------------------------------------------------- 1 | var err = new Error("Something happened"); 2 | err.info = "Additional info"; 3 | var nonerr = Object.create(err); 4 | console.log(err); 5 | console.log(nonerr); 6 | 7 | var util = require("util"); 8 | console.log(util.isError(err)); 9 | console.log(util.isError(nonerr)); 10 | 11 | -------------------------------------------------------------------------------- /res/experiments/2013-09-22-efs-plugin-api.js: -------------------------------------------------------------------------------- 1 | 2 | var API = {}; 3 | 4 | // No good. 5 | API.on("request", function(req, res) { 6 | 7 | }); 8 | 9 | API.registerWebPath = function(path, callback) {}; 10 | 11 | 12 | -------------------------------------------------------------------------------- /res/experiments/2014-01-22-earthfs-internal-file.txt: -------------------------------------------------------------------------------- 1 | EarthFS internal file 2 | Dedicated to Grandma 3 | "Read and learn" 4 | -------------------------------------------------------------------------------- /res/experiments/2014-02-04-link-tracking.txt: -------------------------------------------------------------------------------- 1 | CREATE TEMPORARY TABLE "deepLinks" ( 2 | "deepLinkID" bigint NOT NULL, 3 | "sourceURIID" bigint NOT NULL, 4 | "targetURIID" bigint NOT NULL, 5 | "distance" bigint NOT NULL, 6 | ); 7 | CREATE SEQUENCE "deepLinks_deepLinkID_seq" 8 | START WITH 1 9 | INCREMENT BY 1 10 | NO MINVALUE 11 | NO MAXVALUE 12 | CACHE 1; 13 | 14 | INSERT INTO "signatures" () 15 | SELECT ... 16 | FROM 17 | 18 | INSERT INTO "deepLinks" ("sourceURIID", "targetURIID", "distance") 19 | SELECT l."sourceURIID", l."targetURIID", 1 20 | FROM "links" AS l 21 | WHERE 22 | 23 | function deepLinks(userID) { 24 | db.query('CREATE TEMPORARY TABLE ...'); 25 | db.query(' 26 | } 27 | 28 | -------------------------------------------------------------------------------- /res/experiments/2014-05-22-easy-http-parser.c: -------------------------------------------------------------------------------- 1 | 2 | typedef char str_t; 3 | 4 | typedef void (*header_cb)(void *const context, str_t const *const field, str_t const *const value); 5 | 6 | #define HEADER_MAX_FIELD 40 7 | #define HEADER_MAX_VALUE 1024 8 | 9 | typedef struct { 10 | // Public 11 | header_cb callback; 12 | void *context; 13 | 14 | // Private 15 | str_t field[HEADER_MAX_FIELD]; 16 | size_t field_length; 17 | str_t value[HEADER_MAX_VALUE]; 18 | size_t value_length; 19 | } header_parser; 20 | 21 | static void header_emit(header_parser *const parser) { 22 | parser->callback(parser->context, &parser->field, &parser->value); 23 | memset(&parser->field, 0, parser->field_length); 24 | memset(&parser->value, 0, parser->value_length); 25 | parser->field_length = 0; 26 | parser->value_length = 0; 27 | } 28 | 29 | void header_parse_field(header_parser *const parser, char const *const at, size_t const len) { 30 | if(parser->value_length) header_emit(parser); 31 | size_t safeLen = MIN(len, HEADER_MAX_FIELD - parser->field_length); 32 | memcpy(parser->field + parser->field_length, at, safeLen); 33 | parser->field_length += safeLen; 34 | } 35 | void header_parse_value(header_parser *const parser, char const *const at, size_t const len) { 36 | size_t safeLen = MIN(len, HEADER_MAX_VALUE - parser->value_length); 37 | memcpy(parser->value + parser->value_length, at, safeLen); 38 | parser->value_length += safeLen; 39 | } 40 | void header_parse_done(header_parser *const parser) { 41 | if(parser->field_length || parser->value_length) header_emit(parser); 42 | } 43 | 44 | -------------------------------------------------------------------------------- /res/experiments/2014-05-23-efs-rest-api.c: -------------------------------------------------------------------------------- 1 | 2 | void HTTPResponseBegin(fd_t const stream, uint16_t const status, str_t const *const message) { 3 | // TODO: TCP_CORK? 4 | str_t *str; 5 | BTErrno(asprintf(&str, "HTTP/1.1 %d %s\r\n", status, message); 6 | write(stream, str, strlen(str)); 7 | free(str); 8 | } 9 | void HTTPHeaderWrite(fd_t const stream, str_t const *const field, str_t const *const value) { 10 | write(stream, field, strlen(field)); 11 | write(stream, ": ", 2); 12 | write(stream, value, strlen(value)); 13 | write(stream, "\r\n", 2); 14 | } 15 | void HTTPResponseEnd(fd_t const stream) { 16 | HTTPHeaderWrite(stream, "Connection", "close"); 17 | write(stream, "\r\n", 2); // TODO: Safe for HEAD requests? 18 | // TODO: TCP_CORK? 19 | } 20 | 21 | 22 | static bool_t getFile(fd_t const res, str_t const *const method, str_t const *const URI) { 23 | 24 | // TODO: How are we supposed to access our headers? 25 | 26 | if(strcasecmp("GET", method)) return false; 27 | 28 | HTTPResponseBegin(res, 200, "OK"); 29 | HTTPHeaderWrite(res, "Content-Type", "text/plain; charset=utf-8"); 30 | HTTPResponseEnd(res); 31 | sendfile(); 32 | close(res); 33 | 34 | return true; 35 | } 36 | 37 | -------------------------------------------------------------------------------- /res/experiments/2014-06-02-querystring.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | void doSomething(str_t const *const qs) { 4 | str_t const *rest = qs; 5 | for(;;) { 6 | if('\0' == rest[0]) break; // Or other length check. 7 | if('#' == rest[0]) break; 8 | // just check for ? and & ? 9 | } 10 | } 11 | 12 | 13 | -------------------------------------------------------------------------------- /res/experiments/2014-06-03-efs-db-test.db: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2014-06-03-efs-db-test.db -------------------------------------------------------------------------------- /res/experiments/2014-06-04-dstr.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct { 3 | uint16_t length; 4 | uint16_t size; 5 | str_t value[0]; 6 | } dstr_t; 7 | 8 | void dstr_append(dstr_t const dst, dstr_t const src) { 9 | 10 | } 11 | 12 | -------------------------------------------------------------------------------- /res/experiments/2014-06-10-efs-indexer.c: -------------------------------------------------------------------------------- 1 | 2 | // abandoned, see 2014-06-10-efs-uri-list-parser.c 3 | 4 | typedef struct EFSIndexer* EFSIndexerRef; 5 | 6 | struct EFSIndexer { 7 | 8 | }; 9 | 10 | EFSIndexerRef EFSIndexerCreate(strarg_t const type) { 11 | if(!type) return NULL; 12 | if(!prefix("text/", type)) return NULL; // TODO: Indexers for other types. 13 | EFSIndexerRef const indexer = calloc(1, sizeof(struct EFSIndexer)); 14 | 15 | 16 | return indexer; 17 | } 18 | void EFSIndexerWrite(EFSIndexerRef const indexer, byte_t const *const buf, size_t const len) { 19 | if(!indexer) return; 20 | 21 | } 22 | 23 | 24 | -------------------------------------------------------------------------------- /res/experiments/2014-06-10-hypertext-parser.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | typedef enum { 4 | HT_READY, 5 | HT_READING_SCHEME, 6 | 7 | } hypertext_state; 8 | typedef struct { 9 | 10 | } hypertext_parser; 11 | 12 | 13 | -------------------------------------------------------------------------------- /res/experiments/2014-06-15-headerlist.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct HeaderList* HeaderListRef; 3 | 4 | typedef struct { 5 | str_t *field; 6 | str_t *value; 7 | } Header; 8 | struct HeaderList { 9 | count_t count; 10 | count_t size; 11 | Header *items; 12 | }; 13 | 14 | HeaderListRef HeaderListCreate(void) { 15 | HeaderListRef const list = calloc(1, sizeof(struct HeaderList)); 16 | return list; 17 | } 18 | void HeaderListFree(HeaderListRef const list) { 19 | if(!list) return; 20 | for(index_t i = 0; i < list->count; ++i) { 21 | FREE(&list->items[i].field); 22 | FREE(&list->items[i].value); 23 | } 24 | FREE(&list->items); 25 | free(list); 26 | } 27 | err_t HeaderListAdd(HeaderListRef const list, strarg_t const field, strarg_t const value) { 28 | if(!list) return 0; 29 | if(++list->count > list->size) { 30 | list->size = MAX(10, list->size * 2); 31 | list->items = realloc(list->items, list->size * sizeof(Header)); 32 | if(!list->items) return -1; 33 | memset(list->items[list->count], 0, (list->size - list->count) * sizeof(Header)); 34 | } 35 | list->items[list->count-1].field = strdup(field); 36 | list->items[list->count-1].value = strdup(value); 37 | return 0; 38 | } 39 | strarg_t HeaderListGet(HeaderListRef const list, strarg_t const field) { 40 | if(!list) return NULL; 41 | for(index_t i = 0; i < list->count; ++i) { 42 | if(0 == strcmp(field, list->items[i].field)) return list->items[i].value; 43 | } 44 | return NULL; 45 | } 46 | 47 | 48 | 49 | -------------------------------------------------------------------------------- /res/experiments/2014-06-15-headers.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct { 3 | strarg_t const name; 4 | size_t const size; 5 | } HeaderField; 6 | typedef struct { 7 | count_t count; 8 | HeaderField *items; 9 | } HeaderFieldList; 10 | 11 | typedef struct { 12 | str_t *content_type; 13 | } EFSHeaders; 14 | static HeaderField const EFSHeaderFields[] = { 15 | {"content-type", 100}, 16 | }; 17 | static HeaderFieldList const EFSHeaderFieldList = { 18 | .count = numberof(EFSHeaderFields), 19 | .items = &EFSHeaderFields, 20 | }; 21 | 22 | 23 | -------------------------------------------------------------------------------- /res/experiments/2014-06-23-htmlenc.c: -------------------------------------------------------------------------------- 1 | static str_t *htmlenc(strarg_t const str) { 2 | size_t total = 0; 3 | for(off_t i = 0; str[i]; ++i) switch(str[i]) { 4 | case '<': total += 4; break; 5 | case '>': total += 4; break; 6 | case '&': total += 5; break; 7 | case '"': total += 6; break; 8 | default: total += 1; break; 9 | } 10 | str_t *enc = malloc(total+1); 11 | for(off_t i = 0, j = 0; str[i]; ++i) switch(str[i]) { 12 | case '<': memcpy(enc+j, "<", 4); j += 4; break; 13 | case '>': memcpy(enc+j, ">", 4); j += 4; break; 14 | case '&': memcpy(enc+j, "&", 5); j += 5; break; 15 | case '"': memcpy(enc+j, """, 6); j += 6; break; 16 | default: enc[j++] = str[i]; break; 17 | } 18 | enc[total] = '\0'; 19 | return enc; 20 | } 21 | 22 | -------------------------------------------------------------------------------- /res/experiments/2014-06-23-uv-printf.c: -------------------------------------------------------------------------------- 1 | typedef err_t (*write_fn)(void *ctx, byte_t const *const buf, size_t const len); 2 | 3 | #include 4 | 5 | err_t wprintf(write_fn const write, void *const ctx, strarg_t const fmt, ...) { 6 | va_list args = va_start(fmt); 7 | err_t const r = async_vprintf(write, ctx, fmt, args); 8 | va_end(args); 9 | return r; 10 | } 11 | err_t vwprintf(write_fn const write, void *const ctx, strarg_t const fmt, va_list args) { 12 | strarg_t pos = fmt; 13 | off_t i = 0; 14 | for(;;) { 15 | if('\0' != pos[i] && '%' != pos[i]) { ++i; continue; } 16 | if(i) { 17 | if(write(ctx, (byte_t const *)pos, i) < 0) return -1; 18 | pos += i; 19 | i = 0; 20 | } 21 | if('\0' == pos[0]) break; 22 | switch(pos[1]) { 23 | case 's': 24 | strarg_t const str = va_arg(args, strarg_t); 25 | if(write(ctx, (byte_t const *)str, strlen(str)) < 0) return -1; 26 | pos += 2; 27 | break; 28 | default: 29 | BTAssert(0, "Format specifier %%%c not yet implemented", pos[1]); 30 | return -1; 31 | } 32 | } 33 | return 0; 34 | } 35 | 36 | -------------------------------------------------------------------------------- /res/experiments/2014-06-24-event-attributes.js: -------------------------------------------------------------------------------- 1 | // http://www.w3schools.com/tags/ref_eventattributes.asp 2 | var eventAttributes = [ 3 | // Window Event Attributes 4 | "onafterprint", "onbeforeprint", "onbeforeunload", "onerror", "onhaschange", "onload", "onmessage", "onoffline", "ononline", "onpagehide", "onpageshow", "onpopstate", "onredo", "onresize", "onstorage", "onundo", "onunload", 5 | // Form Events 6 | "onblur", "onchange", "oncontextmenu", "onfocus", "onformchange", "onforminput", "oninput", "oninvalid", "onreset", "onselect", "onsubmit", 7 | // Keyboard Events 8 | "onkeydown", "onkeypress", "onkeyup", 9 | // Mouse Events 10 | "onclick", "ondblclick", "ondrag", "ondragend", "ondragenter", "ondragleave", "ondragover", "ondragstart", "ondrop", "onmousedown", "onmousemove", "onmouseout", "onmouseover", "onmouseup", "onmousewheel", "onscroll", 11 | // Media Events 12 | "onabort", "oncanplay", "oncanplaythrough", "ondurationchange", "onemptied", "onended", "onerror", "onloadeddata", "onloadedmetadata", "onloadstart", "onpause", "onplay", "onplaying", "onprogress", "onratechange", "onreadystatechange", "onseeked", "onseeking", "onstalled", "onsuspend", "ontimeupdate", "onvolumechange", "onwaiting" 13 | ]; 14 | 15 | -------------------------------------------------------------------------------- /res/experiments/2014-06-24-http-io.c: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2014-06-24-http-io.c -------------------------------------------------------------------------------- /res/experiments/2014-06-29-headers.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct Headers* HeadersRef; 3 | 4 | typedef enum { 5 | HEADER_FIELD_RETAINED = 1 << 0, 6 | HEADER_VALUE_RETAINED = 1 << 1, 7 | } HeaderFlags; 8 | typedef struct { 9 | strarg_t field; 10 | size_t flen; 11 | strarg_t value; 12 | size_t vlen; 13 | HeaderFlags flags; 14 | } Header; 15 | struct Headers { 16 | count_t count; 17 | count_t size; 18 | Header *items; 19 | }; 20 | 21 | HeadersRef HeadersCreate(void) { 22 | 23 | } 24 | 25 | -------------------------------------------------------------------------------- /res/experiments/2014-06-29-session-cache.c: -------------------------------------------------------------------------------- 1 | #define COOKIE_CACHE_SIZE 1000 2 | 3 | struct cached_cookie { 4 | int64_t sessionID; 5 | str_t *sessionKey; 6 | uint64_t atime; 7 | }; 8 | static cached_cookie cookies[COOKIE_CACHE_SIZE] = {}; 9 | 10 | 11 | -------------------------------------------------------------------------------- /res/experiments/2014-07-01-connection-pool.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct async_db_pool_s async_db_pool_t; 3 | 4 | struct async_db_pool_s { 5 | struct { 6 | unsigned size; 7 | sqlite3 **items; 8 | unsigned cur; 9 | unsigned count; 10 | } connections; 11 | struct { 12 | unsigned size; 13 | cothread_t *items; 14 | unsigned cur; 15 | unsigned count; 16 | } queue; 17 | }; 18 | 19 | async_db_pool_t *async_db_pool_create(unsigned const count) { 20 | 21 | } 22 | 23 | -------------------------------------------------------------------------------- /res/experiments/2014-07-19-test-data.sql: -------------------------------------------------------------------------------- 1 | 2 | INSERT INTO file_uris (file_id, uri) VALUES (0, 'hash://test/0123456789012345678901234567890123456789'); 3 | 4 | 5 | -------------------------------------------------------------------------------- /res/experiments/2014-07-20-query-parser.txt: -------------------------------------------------------------------------------- 1 | start <- exp* !. 2 | 3 | exp <- link 4 | 5 | link <- < scheme '://' [^ \n\t] > { fprintf(stderr, "%s\n", yytext); } 6 | 7 | scheme <- [a-z0-9-]+ 8 | 9 | 10 | # hash://asdf/asdf 11 | # first, list the file, then list the files that link to it 12 | 13 | 14 | -------------------------------------------------------------------------------- /res/experiments/2014-07-26-async-sqlite-pool.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct async_sqlite3_pool async_sqlite3_pool; 3 | typedef struct async_sqlite3 4 | 5 | #include "async.h" 6 | 7 | typedef enum { 8 | t_prepare, 9 | t_step, 10 | } req_type; 11 | 12 | typedef struct { 13 | req_type type; 14 | 15 | } prepare_req; 16 | typedef struct { 17 | req_type type; 18 | 19 | } step_req; 20 | 21 | typedef union { 22 | prepare_req prepare; 23 | step_req step; 24 | } request; 25 | 26 | typedef struct { 27 | uv_thread_t *thread; 28 | request *req; 29 | uv_cond_t worker; 30 | uv_async_t main; 31 | } worker_state; 32 | 33 | struct async_sqlite3_pool { 34 | unsigned count; 35 | async_sqlite3 **connections; 36 | uv_thread_t **threads; 37 | }; 38 | struct async_sqlite3 { 39 | sqlite3 *connection; 40 | }; 41 | 42 | 43 | 44 | 45 | int async_sqlite3_prepare_v2(async_sqlite3 *db, const char *zSql, int nByte, sqlite3_stmt **ppStmt, const char **pzTail) { 46 | 47 | } 48 | 49 | 50 | 51 | -------------------------------------------------------------------------------- /res/experiments/2014-08-16-query-tests.sql: -------------------------------------------------------------------------------- 1 | CREATE TEMPORARY VIEW x AS 2 | SELECT f.file_id AS file_id, MIN(mf.file_id) AS age 3 | FROM fulltext AS ft 4 | INNER JOIN meta_fulltext AS mft 5 | ON (mft.docid = ft.docid) 6 | INNER JOIN meta_files AS mf 7 | ON (mf.meta_file_id = mft.meta_file_id) 8 | INNER JOIN file_uris AS f 9 | ON (f.uri = mf.target_uri) 10 | WHERE ft.value MATCH 'slow' 11 | GROUP BY f.file_id 12 | 13 | 14 | select * 15 | from x 16 | inner join y 17 | on x.file_id = y.file_id 18 | 19 | 20 | CREATE TEMPORARY VIEW y AS 21 | SELECT f.file_id AS file_id, MIN(mf.file_id) AS age 22 | FROM fulltext AS ft 23 | INNER JOIN meta_fulltext AS mft 24 | ON (mft.docid = ft.docid) 25 | INNER JOIN meta_files AS mf 26 | ON (mf.meta_file_id = mft.meta_file_id) 27 | INNER JOIN file_uris AS f 28 | ON (f.uri = mf.target_uri) 29 | WHERE ft.value MATCH 'fast' 30 | GROUP BY f.file_id 31 | 32 | -------------------------------------------------------------------------------- /res/experiments/2014-08-18-efs-dump.c: -------------------------------------------------------------------------------- 1 | #include "../deps/liblmdb/lmdb.h" 2 | #include "../src/db.h" 3 | 4 | int main(int const argc, char const *const *const argv) { 5 | 6 | MDB_env *env = NULL; 7 | mdb_env_create(&env); 8 | mdb_env_set_maxdbs(conn->env, 32); 9 | mdb_env_open(env, "/home/ben/Documents/testrepo/efs.db", MDB_NOSUBDIR, 0600); 10 | 11 | MDB_dbi userByID, userIDByName; 12 | mdb_dbi_open(env, "userByID", 0, &userByID); 13 | mdb_dbi_open(env, "userIDByName", 0, &userIDByName); 14 | 15 | MDB_txn *txn = NULL; 16 | mdb_txn_begin(env, NULL, MDB_RDONLY, &txn); 17 | 18 | MDB_cursor *cur = NULL; 19 | mdb_cursor_open(txn, userByID, &cur); 20 | 21 | MDB_val userID_val; 22 | MDB_val user_val; 23 | int rc = mdb_cursor_get(cur, &userID_val, &user_val, MDB_FIRST); 24 | for(; MDB_SUCCESS == rc; rc = mdb_cursor_get(cur, &userID_val, &user_val, MDB_NEXT)) { 25 | 26 | 27 | int64_t const userID = db_read_int64(&userID_val); 28 | strarg_t const username = db_read_text(&user_val); 29 | strarg_t const passhash = db_read_text(&user_val); 30 | strarg_t const token = db_read_text(&user_val); 31 | 32 | 33 | fprintf(stdout, "%lld: %s, %s, %s\n", userID, username, passhash, token); 34 | 35 | 36 | } 37 | 38 | return EXIT_SUCCESS; 39 | } 40 | 41 | 42 | -------------------------------------------------------------------------------- /res/experiments/2014-08-27-efspush.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct EFSPush* EFSPushRef; 3 | 4 | struct EFSPush { 5 | EFSRepoRef repo; 6 | uint64_t sequence; 7 | 8 | }; 9 | 10 | EFSSubmissionRef EFSPushWait(EFSPushRef const push) { 11 | assert(push); 12 | EFSRepoRef const repo = push->repo; 13 | // messing with internal repo state... 14 | } 15 | 16 | 17 | -------------------------------------------------------------------------------- /res/experiments/2014-08-29-filters.sql: -------------------------------------------------------------------------------- 1 | SELECT mft.docid, mft.meta_file_id, f.file_id 2 | FROM fulltext AS ft 3 | JOIN meta_fulltext AS mft ON (mft.docid = ft.docid) 4 | JOIN meta_files AS mf ON (mf.meta_file_id = mft.meta_file_id) 5 | JOIN file_uris AS f ON (f.uri = mf.target_uri) 6 | WHERE ft.value MATCH "obscure" 7 | ORDER BY ft.docid DESC 8 | 9 | 10 | 11 | -------------------------------------------------------------------------------- /res/experiments/2014-09-05-efs-submission-wait.c: -------------------------------------------------------------------------------- 1 | 2 | #define QUERY_TIMEOUT_MS (1000 * 30) 3 | 4 | typedef struct thread_list thread_list; 5 | struct thread_list { 6 | cothread_t thread; 7 | thread_list *next; 8 | }; 9 | 10 | 11 | struct EFSRepo { 12 | 13 | 14 | thread_list *queries_head; 15 | thread_list *queries_tail; 16 | uv_timer_t query_timeout; 17 | EFSSubmissionRef sub_queue[10]; 18 | }; 19 | 20 | 21 | EFSSubmissionRef EFSRepoSubmissionWait(EFSRepoRef const repo) { 22 | assert(repo); 23 | thread_list us = { 24 | .thread = co_active(), 25 | .next = NULL, 26 | }; 27 | if(repo->queries_tail) { 28 | repo->queries_tail.next = &us; 29 | repo->queries_tail = &us; 30 | timeout = uv_now(loop) + QUERY_TIMEOUT_MS; 31 | } else { 32 | repo->queries_head = &us; 33 | repo->queries_tail = &us; 34 | timeout = 0; 35 | uv_timer_start(&repo->query_timeout, timeout_cb, QUERY_TIMEOUT_MS, 0); 36 | } 37 | async_yield(); 38 | EFSSubmissionRef sub = NULL; 39 | if(repo->sub_queue[x]) sub = repo->sub_queue[x]; 40 | if(!sub && uv_now(loop) < timeout) { 41 | uv_timer_start(&repo->query_timeout, timeout_cb, timeout - uv_now(loop), 0); 42 | async_yield(); 43 | if(repo->sub_queue[x]) sub = repo->sub_queue[x]; 44 | } 45 | assert(&us == repo->queries_head); 46 | repo->queries_head = us.next; 47 | if(&us == repo->queries_tail) repo->queries_tail = NULL; 48 | if(us.next) async_wakeup(us.next); 49 | else repo->x++; 50 | return sub; 51 | } 52 | 53 | 54 | 55 | 56 | 57 | 58 | -------------------------------------------------------------------------------- /res/experiments/2014-09-06-query.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | struct EFSRepo { 5 | 6 | 7 | 8 | async_mutex_t *sub_mutex; 9 | async_cond_t *sub_cond; 10 | uint64_t sub_latest; 11 | }; 12 | 13 | void EFSRepoSubmissionEmit(EFSRepoRef const repo, uint64_t const sortID) { 14 | assert(repo); 15 | async_mutex_lock(repo->sub_mutex); 16 | assert(sortID > repo->sub_latest); 17 | repo->sub_latest = sortID; 18 | async_cond_broadcast(repo->sub_cond); 19 | async_mutex_unlock(repo->sub_mutex); 20 | } 21 | bool_t EFSRepoSubmissionWait(EFSRepoRef const repo, uint64_t const sortID, uint64_t const future) { 22 | assert(repo); 23 | async_mutex_lock(repo->sub_mutex); 24 | while(repo->sub_latest <= sortID && async_cond_timedwait(repo->sub_cond, repo->sub_mutex, future) < 0); 25 | bool_t const res = repo->sub_latest > sortID; 26 | async_mutex_unlock(repo->sub_mutex); 27 | return res; 28 | } 29 | 30 | -------------------------------------------------------------------------------- /res/experiments/2014-09-18-pmap.c: -------------------------------------------------------------------------------- 1 | struct work { 2 | void **inputs; 3 | void **outputs; 4 | }; 5 | static void pmap_worker(void *ctx) { 6 | struct work *const work = ctx; 7 | co_switch(yield); 8 | for(;;) { 9 | async_worker_enter(?); 10 | 11 | 12 | async_worker_leave(?); 13 | co_switch(); 14 | } 15 | } 16 | 17 | 18 | void async_worker_pmap() { 19 | 20 | } 21 | 22 | // forget this 23 | // each worker should have a built-in fiber that it can use 24 | 25 | 26 | void async_worker_background(async_worker_t *worker, void (*work)(void *), void (*done)(void *), void *ctx); 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | -------------------------------------------------------------------------------- /res/experiments/2014-09-19-stress.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | var http = require("http"); 4 | var urlModule = require("url"); 5 | 6 | var url = process.argv[2]; 7 | var total = 1000; 8 | var data = 0; 9 | var statuses = {}; 10 | 11 | if(!url) throw new Error("No URL"); 12 | http.globalAgent.maxSockets = 100; 13 | 14 | function get(obj) { 15 | var req = http.get(obj); 16 | req.on("response", function(res) { 17 | var status = res.statusCode; 18 | if(!statuses[status]) statuses[status] = 1; 19 | else statuses[status]++; 20 | res.on("readable", function() { 21 | var x = res.read(); 22 | data += x.length; 23 | // console.log(x.toString("utf8")); 24 | }); 25 | // res.on("end", function() { 26 | // }); 27 | }); 28 | req.on("error", function(err) { 29 | if(!statuses["conn"]) statuses["conn"] = 1; 30 | else statuses["conn"]++; 31 | }); 32 | } 33 | 34 | var obj = urlModule.parse(url); 35 | obj.headers = { "Cookie": "s=1:not-very-random" }; 36 | var then = +new Date; 37 | for(var i = 0; i < total; ++i) { 38 | get(obj); 39 | } 40 | 41 | process.on("exit", function() { 42 | var duration = (+new Date - then) / 1000.0; 43 | console.log("Seconds: "+duration); 44 | console.log("Req/s: "+(total / duration)); 45 | console.log("KB/s: "+((data / 1024) / duration)); 46 | console.log("Statuses:", statuses); 47 | }); 48 | 49 | -------------------------------------------------------------------------------- /res/experiments/2014-09-23-mdb-email.txt: -------------------------------------------------------------------------------- 1 | Nested b-trees (to write an LSM-tree wrapper for MDB) 2 | 3 | Hi, 4 | 5 | I've been working on a thin wrapper for MDB that provides LSM-tree support. My goal is to have multiple named b-trees and LSM-trees in the same file, support transactions across both, etc. 6 | 7 | However, all of the approaches I've come up with have problems: 8 | 9 | 1. (What I started with) Prefix keys with the level number. Requires lots of management, e.g. preventing cursors from wrapping between layers, and probably slow because everything is in one big tree (can't use MDB_APPEND during merges). 10 | 2. Use multiple DBIs per LSM-tree. Would be uglier and the docs warn about creating large numbers of DBIs. 11 | 3. Use dupsort. Would be perfect if it were possible to store values for each nested key. There is plenty of "spare key-space" for the wrapper to store its own meta-data without it getting in the way. 12 | 13 | In my research of different databases, MDB seems like the best b-tree implementation. Thus an LSM-tree built on top of it would probably also be the best option for random-write workloads. If MDB exposed the support for nested b-trees that it already has, this would be possible. 14 | 15 | By contrast something like LevelDB is larger, less parallel and doesn't support transactions. 16 | 17 | Ben Trask 18 | 19 | 20 | -------------------------------------------------------------------------------- /res/experiments/2014-09-24-mdb-feature-requests.txt: -------------------------------------------------------------------------------- 1 | Feature requests: 2 | 3 | 1. mdb_get_op() which accepts stateless cursor ops (i.e. first/last/range) 4 | 2. mdb_txn_flags() function to tell if a transaction is read-only (akin to mdb_dbi_flags()) 5 | 3. Allow cursors to be reused across write transactions, or at least don't silently free them and have mdb_cursor_renew() indicate an error so they can manually be recreated (would be less of an issue if there were a way to tell which transactions were read-only) 6 | 4. First class nested b-trees, beyond just dupsort 7 | 5. Constant-time mdb_drop() (just add the whole tree to the free list as-is) 8 | 9 | Bug reports: 10 | 11 | 1. MDB_PREV_DUP is broken (wrong indentation of else clause) 12 | 2. Failing to pass a data argument for dupsort tables sometimes has side effects (leaving the xcursor uninitialized/unchanged) 13 | 14 | 15 | -------------------------------------------------------------------------------- /res/experiments/2014-10-01-lsmdb.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | typedef struct LSMDB_env LSMDB_env; 4 | typedef struct LSMDB_txn LSMDB_txn; 5 | typedef struct LSMDB_cursor LSMDB_cursor; 6 | 7 | 8 | #define DEPTH_MAX 16 9 | 10 | 11 | struct LSMDB_env { 12 | MDB_env *env; 13 | MDB_dbi dbis[DEPTH_MAX*2]; 14 | }; 15 | struct LSMDB_txn { 16 | LSMDB_env *env; 17 | LSMDB_txn *parent; 18 | MDB_txn *txn; 19 | 20 | LSMDB_level depth; 21 | LSMDB_cursor *cursor; 22 | MDB_cursor *merge; 23 | }; 24 | struct LSMDB_cursor { 25 | LSMDB_txn *txn; 26 | MDB_cursor *cursors[DEPTH_MAX]; 27 | LSMDB_level sorted[DEPTH_MAX]; 28 | }; 29 | 30 | -------------------------------------------------------------------------------- /res/experiments/2014-10-12-swap.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | typedef enum { 6 | LSMDB_NONE = 0, 7 | LSMDB_ABC = 1, 8 | LSMDB_ACB = 2, 9 | LSMDB_BAC = 3, 10 | LSMDB_BCA = 4, 11 | LSMDB_CAB = 5, 12 | LSMDB_CBA = 6, 13 | } LSMDB_state; 14 | 15 | static LSMDB_state lsmdb_swap_12(LSMDB_state const x) { 16 | switch(x) { 17 | case LSMDB_ABC: return LSMDB_BAC; 18 | case LSMDB_ACB: return LSMDB_CAB; 19 | case LSMDB_BAC: return LSMDB_ABC; 20 | case LSMDB_BCA: return LSMDB_CBA; 21 | case LSMDB_CAB: return LSMDB_ACB; 22 | case LSMDB_CBA: return LSMDB_BCA; 23 | default: assert(0); return 0; 24 | } 25 | } 26 | static LSMDB_state lsmdb_swap_23(LSMDB_state const x) { 27 | switch(x) { 28 | case LSMDB_ABC: return LSMDB_ACB; 29 | case LSMDB_ACB: return LSMDB_ABC; 30 | case LSMDB_BAC: return LSMDB_BCA; 31 | case LSMDB_BCA: return LSMDB_BAC; 32 | case LSMDB_CAB: return LSMDB_CBA; 33 | case LSMDB_CBA: return LSMDB_CAB; 34 | default: assert(0); return 0; 35 | } 36 | } 37 | 38 | -------------------------------------------------------------------------------- /res/experiments/2014-10-28-sorted-map.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | typedef struct omap_t omap_t; 4 | 5 | int omap_create(omap_t **const out); 6 | int omap_count(omap_t *const omap); 7 | int omap_index(omap_t *const omap, unsigned const index, DB_val *const key, DB_val *const data); 8 | int omap_key(omap_t *const omap, DB_val const *const key, DB_val *const data); 9 | 10 | -------------------------------------------------------------------------------- /res/experiments/2014-11-18-efs-fts.c: -------------------------------------------------------------------------------- 1 | 2 | #define EFS_FTS_TOKEN_MAX 20 3 | #define EFS_FTS_VAL(name) \ 4 | uint8_t __buf_##name[DB_VARINT_MAX*3 + EFS_FTS_TOKEN_MAX]; \ 5 | DB_val name[1] = {{ 0, __buf_##name }} 6 | #define EFS_FTS_RANGE(name) \ 7 | EFS_FTS_VAL(__min_##name); \ 8 | EFS_FTS_VAL(__max_##name); \ 9 | DB_range name[1] = {{ __min_##name, __max_##name }} 10 | 11 | 12 | void efs_fts_bind(DB_val *const key, strarg_t const token, size_t const len, uint64_t const metaFileID, uint64_t const offset) { 13 | assert(0 == key->size); 14 | assert(NULL != key->data); 15 | byte_t *pos = key->data + key->size; 16 | 17 | pos += varint_encode(pos, SIZE_MAX, EFSTermMetaFileIDAndPosition); 18 | memcpy(pos, token, len); 19 | pos += len; 20 | *pos++ = '\0'; 21 | // pos += varint_encode(pos, SIZE_MAX, metaFileID); 22 | // pos += varint_encode(pos, SIZE_MAX, 0); // TODO: Record offset. Requires changes to EFSFulltextFilter so that each document only gets returned once, no matter how many times the token appears within it. 23 | 24 | key->size = pos - key->data; 25 | } 26 | uint64_t efs_fts_column_metaFileID 27 | 28 | 29 | 30 | 31 | void EFSFTSBind(DB_val *const key, strarg_t const token, size_t const len); 32 | void EFSFTSRange(DB_range *const range); // BAD 33 | strarg_t EFSFTSToken(DB_val *const key); 34 | uint64_t EFSFTSMetaFileID(DB_val *const key); 35 | uint64_t EFSFTSOffset(DB_val *const key); 36 | 37 | 38 | 39 | 40 | void db_bind_string(DB_val *const val, strarg_t const token, size_t const len); 41 | 42 | uint64_t db_column_next(); 43 | strarg_t db_column_next_string(); 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | -------------------------------------------------------------------------------- /res/experiments/2015-01-01-stronglink-interface.h: -------------------------------------------------------------------------------- 1 | 2 | 3 | SLIRepo *SLIRepoOpen(); 4 | SLIRepoRef SLIRepoOpen(); 5 | SLI_repo *sli_repo_open(); 6 | 7 | -------------------------------------------------------------------------------- /res/experiments/2015-01-09-push.c: -------------------------------------------------------------------------------- 1 | 2 | struct EFSPush { 3 | uint64_t pushID; 4 | EFSSessionRef session; 5 | str_t *host; 6 | str_t *username; 7 | str_t *password; 8 | str_t *cookie; 9 | str_t *query; 10 | 11 | HTTPConnectionRef conn; 12 | HTTPMessageRef msg; 13 | 14 | EFSFilterRef filter; 15 | 16 | }; 17 | 18 | 19 | 20 | EFSPushRef EFSRepoCreatePush(EFSRepoRef const repo, uint64_t const pullID, uint64_t const userID, strarg_t const host, strarg_t const username, strarg_t const password, strarg_t const cookie, strarg_t const query) { 21 | 22 | 23 | } 24 | void EFSPushFree() {} 25 | 26 | 27 | static int head(EFSPushRef const push, HTTPConnectionRef const conn, strarg_t const URI) { 28 | HTTPMessageRef const head = HTTPMessageCreate(conn); 29 | if(!head) return -1; 30 | HTTPMessageWriteRequest(head, HTTP_HEAD, "/efs/file/asdf/asdf", push->host); 31 | HTTPMessageBeginBody(head); 32 | HTTPMessageEnd(head); 33 | return HTTPMessageGetResponseStatus(head); 34 | } 35 | static err_t post(EFSPushRef const push, HTTPConnectionRef const conn, strarg_t const URI) { 36 | EFSFileInfo info[1]; 37 | err_t rc = EFSSessionGetFileInfo(push->session, URI, info); 38 | if(rc < 0) return rc; 39 | 40 | } 41 | static err_t submit(EFSPushRef const push, HTTPConnectionRef const conn, strarg_t const URI) { 42 | int const status = head(push, conn, URI); 43 | if(status < 0) return status; 44 | if(status > 0) return 0; // Already submitted. 45 | return post(push, conn, URI); 46 | // Not going to work, thundering herd. 47 | } 48 | static err_t connect() { 49 | 50 | } 51 | err_t EFSPushStart(EFSPushRef const push) { 52 | 53 | } 54 | 55 | 56 | 57 | 58 | -------------------------------------------------------------------------------- /res/experiments/2015-02-10-select.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | { 7 | 8 | 9 | 10 | async_read_t r1[1]; 11 | async_read_t r2[1]; 12 | async_select_t sel[1]; 13 | async_read_for_select(sel, r1, stream1); 14 | async_read_for_select(sel, r2, stream2); 15 | void *const ptr = select(sel); 16 | async_read_stop(r1); 17 | async_read_stop(r2); 18 | if(r1 == ptr) { 19 | 20 | } else if(r2 == ptr) { 21 | 22 | } 23 | 24 | // this is just... crazy 25 | // well, useless 26 | // it doesn't help with what we want to do at all 27 | 28 | } 29 | 30 | 31 | -------------------------------------------------------------------------------- /res/experiments/2015-02-19-async-read-new.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | // current 4 | int async_read(async_read_t *const req, uv_stream_t *const stream); 5 | 6 | // goal: get rid of request object, now that fibers are directly cancelable 7 | 8 | 9 | int async_read(uv_stream_t *const stream, uv_buf_t *const out); 10 | // direct translation 11 | 12 | 13 | 14 | -------------------------------------------------------------------------------- /res/experiments/2015-02-27-cookie.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | typedef struct { 5 | str_t *name; 6 | str_t *value; 7 | str_t *path; 8 | uint64_t maxage; 9 | } cookie_t; 10 | 11 | int cookie_init(cookie_t *const cookie, strarg_t const str) { 12 | if(!str) return -1; 13 | strarg_t mark = str; 14 | strarg_t x = str; 15 | while('\0' != *x && '=' != *x) x++; 16 | if(x <= mark) goto err; 17 | cookie->name = strndup(mark, x-mark); 18 | if(!name) goto err; 19 | mark = x; 20 | while('\0' != *x && ';' != *x) x++; 21 | if(x <= mark) goto err; 22 | cookie->value = strndup(mark, x-mark); 23 | if(!cookie->value) goto err; 24 | 25 | cookie->path = NULL; 26 | cookie->maxage = 0; 27 | // TODO: Parse other fields 28 | /*while(';' == *x) { 29 | mark = x; 30 | while('\0' != *x && '=' != *x) x++; 31 | }*/ 32 | return 0; 33 | 34 | err: 35 | cookie_destroy(cookie); 36 | return -1; 37 | } 38 | void cookie_destroy(cookie_t *const) { 39 | if(!cookie) return; 40 | FREE(&cookie->name); 41 | FREE(&cookie->value); 42 | FREE(&cookie->path); 43 | cookie->maxage = 0; 44 | } 45 | 46 | 47 | -------------------------------------------------------------------------------- /res/experiments/2015-03-02-login.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | {{repo-title}} login 4 | 5 | 8 | 9 |
10 | 11 | Username:
12 | Password:
13 | 14 | 15 |
16 | 17 | -------------------------------------------------------------------------------- /res/experiments/2015-03-10-config.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | typedef struct EFSConfiguration *EFSConfigurationRef; 4 | 5 | /* 6 | - number of download fibers per pull 7 | - pull queue size 8 | - max meta-file size 9 | - fsync (show of effort) durable/consistent/fast 10 | - ACID, ACI, ? 11 | - blog results per page 12 | - user query restrictions 13 | */ 14 | // blog settings should be in a separate file, or the same file but parsed separately? 15 | 16 | // this is... shaping up to look pretty ugly 17 | 18 | struct EFSConfiguration { 19 | size_t pull_concurrent_connections; 20 | size_t submissions_per_transaction; 21 | size_t metafile_index_bytes; 22 | enum durability_mode; 23 | }; 24 | 25 | 26 | int EFSConfigurationCreate(uv_file const fd, EFSConfigurationRef *const out) { 27 | assert(out); 28 | if(fd < 0) return UV_EINVAL; 29 | 30 | EFSConfigurationRef conf = calloc(1, sizeof(struct EFSConfiguration)); 31 | if(!conf) return UV_ENOMEM; 32 | int rc = 0; 33 | 34 | uv_buf_t buf[1]; 35 | buf->base = malloc(BUF_LEN); 36 | if(!buf->base) { rc = UV_ENOMEM; goto cleanup; } 37 | buf->len = BUF_LEN; 38 | 39 | ssize_t len; 40 | int64_t pos = 0; 41 | for(;;) { 42 | len = async_fs_read(fd, buf, 1, pos); 43 | if(len < 0) { rc = len; goto cleanup; } 44 | 45 | } 46 | 47 | 48 | 49 | *out = conf; 50 | 51 | cleanup: 52 | 53 | if(rc < 0) EFSConfigurationFree(&conf); 54 | return rc; 55 | } 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | -------------------------------------------------------------------------------- /res/experiments/2015-03-25-asprintf.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | char *aasprintf(char const *const fmt, ...) { 6 | va_list ap; 7 | va_start(ap, fmt); 8 | char *str = vnewsprintf(fmt, ap); 9 | va_end(ap); 10 | return str; 11 | } 12 | char *vaasprintf(char const *const fmt, va_list ap) { 13 | va_list ap2; 14 | va_copy(ap2, ap); 15 | int rc = vsnprintf(NULL, 0, fmt, ap2); 16 | va_end(ap2); 17 | if(rc < 0) return NULL; 18 | char *str = malloc(rc+1); 19 | if(!str) return NULL; 20 | rc = vsnprintf(str, rc+1, fmt, ap); 21 | if(rc < 0) { 22 | free(str); 23 | return NULL; 24 | } 25 | return str; 26 | } 27 | 28 | 29 | 30 | -------------------------------------------------------------------------------- /res/experiments/2015-03-27-dirname.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | // because the standard dirname(3) is from a simpler time... 4 | 5 | 6 | 7 | // we need to use the full path, in case the relative path is "." or something 8 | // a bigger problem is if we start supporting chroot, wont the path be "/"? 9 | 10 | 11 | // one idea is to immediately chdir to the repo dir 12 | // then basically everything can use simple relative paths 13 | // and it works with chroot just fine 14 | 15 | // also in that case we dont have to worry about manaully concatenating strings 16 | // just chdir and then getcwd 17 | // and then we can use standard dirname? 18 | 19 | 20 | 21 | // oh, the problem with this approach 22 | // is that 1. it sucks for a host application when we're running as a library 23 | // and 2. doesnt really work for opening multiple repos at once 24 | // which ought to be supported, even if we currently have no use for it 25 | 26 | 27 | // thus we should support "." or "/" as the repo dir, but not require it 28 | // which means either way the repo itself cant use dirname 29 | 30 | 31 | // we also want to support configurable repo names that arent the same as the directory name 32 | // but i think it's reasonable to have EFSRepoCreate(dir, name) 33 | // and then override name later if need be 34 | 35 | 36 | 37 | // we could do some crazy function 38 | // accept an array of relative/absolute paths 39 | // then scan backwards from the last one until we get a real name 40 | 41 | // separation of concerns, better to have two functions 42 | 43 | 44 | // then even better, portability and windows support... 45 | 46 | 47 | 48 | // okay, practical solution 49 | // use chdir to handle resolution 50 | // but change back afterward...? 51 | 52 | 53 | // still need a portable dirname... 54 | 55 | // lets just look for a library yo 56 | 57 | 58 | 59 | 60 | -------------------------------------------------------------------------------- /res/experiments/2015-04-25-tag-all.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | // TODO 4 | var sln = require("/home/user/Code/stronglink/client/node-sln-client/sln-client"); 5 | 6 | var repo = sln.mainRepo(); 7 | if(!repo) { 8 | console.error("No StrongLink repository configured"); 9 | process.exit(1); 10 | } 11 | 12 | if(process.argv.length < 3) { 13 | console.error("Usage: "+process.argv[1]+" "); 14 | process.exit(1); 15 | } 16 | var query = process.argv.slice(-1)[0]; 17 | var meta = { 18 | "tag": process.argv.slice(2, -1), 19 | }; 20 | 21 | var paused = false; // Even Node 0.12 doesn't support stream.pause() properly. 22 | var stream = repo.createQueryStream(query, { wait: false }); 23 | stream.on("readable", function() { 24 | if(paused) return; 25 | var URI = stream.read(); 26 | if(!URI) return; 27 | paused = true; 28 | // stream.pause(); 29 | repo.submitMeta(URI, meta, function(err, obj) { 30 | paused = false; 31 | // stream.resume(); 32 | if(err) throw err; 33 | console.log(URI); 34 | stream.emit("readable"); // Hack to resume stream 35 | }); 36 | }); 37 | 38 | 39 | -------------------------------------------------------------------------------- /res/experiments/2015-04-26-non-meta-filter.m: -------------------------------------------------------------------------------- 1 | 2 | 3 | typedef struct { 4 | uint64_t sortID; 5 | uint64_t fileID; 6 | } slot; 7 | @interface SLNFileAttributeFilter : SLNFilter 8 | { 9 | slot slots[32]; 10 | } 11 | @end 12 | 13 | @interface SLNURIFilter : SLNFileAttributeFilter 14 | @end 15 | 16 | 17 | 18 | @implementation SLNFileAttributeFilter 19 | - (void)free { 20 | 21 | [super free]; 22 | } 23 | 24 | - (SLNFilter *)unwrap { 25 | return self; 26 | } 27 | 28 | - (int)prepare:(DB_txn *const)txn { 29 | if([super prepare:txn] < 0) return -1; 30 | // ??? 31 | return 0; 32 | } 33 | 34 | 35 | @end 36 | 37 | @implementation SLNURIFilter 38 | - (void)free { 39 | FREE(&URI); 40 | [super free]; 41 | } 42 | 43 | - (SLNFilterType)type { 44 | return SLNURIFilterType; 45 | } 46 | - (strarg_t)stringArg:(index_t const)i { 47 | if(0 == i) return URI; 48 | return NULL; 49 | } 50 | - (int)addStringArg:(strarg_t const)str :(size_t const)len { 51 | if(!URI) { 52 | URI = strndup(str, len); 53 | return 0; 54 | } 55 | return -1; 56 | } 57 | - (void)print:(count_t const)depth { 58 | indent(depth); 59 | fprintf(stderr, "(uri \"%s\")\n", URI); 60 | } 61 | - (size_t)getUserFilter:(str_t *const)data :(size_t const)size :(count_t const)depth { 62 | return wr(data, size, URI); 63 | } 64 | 65 | @end 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | 75 | 76 | 77 | 78 | 79 | 80 | 81 | 82 | 83 | 84 | 85 | 86 | -------------------------------------------------------------------------------- /res/experiments/2015-05-02-hash-anatomy.xcf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2015-05-02-hash-anatomy.xcf -------------------------------------------------------------------------------- /res/experiments/2015-05-14-touch-buffer.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | // i'm trying to figure out the least we can do to force the system to load each mapped page from disk 4 | 5 | // note that mlock has the wrong semantics, on top of being gratuitously slow 6 | // the goal here is not to prevent swapping if the system decides its necessary 7 | // the goal is merely to hint to the system we're going to need the memory soon 8 | // and obviously we'd rather wait on a worker thread than on the main one 9 | 10 | // the basic idea is to mark the buffer volatile and read one byte from each page 11 | // if it's volatile the compiler has to emit the read, even if we dont use the result, right? 12 | // unfortunately i can't read x86 assembly well enough to tell... 13 | // this might be a good time to learn how... 14 | 15 | typedef struct { 16 | void *data; 17 | size_t size; 18 | } DB_val; 19 | 20 | void touch(DB_val const *const buf) { 21 | static size_t pagesize = 0; 22 | if(!pagesize) pagesize = sysconf(_SC_PAGE_SIZE); 23 | volatile char const *const x = buf->data; 24 | if(!x) return; 25 | if(!buf->size) return; 26 | int total = 0; 27 | for(size_t pos = 0; pos < buf->size; pos += pagesize) { 28 | total += x[pos]; 29 | } 30 | printf("%d", total); 31 | } 32 | 33 | int main() { 34 | return 0; 35 | } 36 | 37 | // oh... 38 | // this is truly not a problem 39 | // because when we close the cursor/txn we no longer have the right to touch the database's buffers 40 | // so we must either use them or copy them out before leaving the thread 41 | // i actually knew that, i just forgot 42 | 43 | -------------------------------------------------------------------------------- /res/experiments/2015-05-16-default-port.txt: -------------------------------------------------------------------------------- 1 | 5726 2 | 3 | 4 | 9900 5 | 9009 6 | 7 | 8 | 8900 9 | 10 | 6400 11 | 6432 12 | 13 | 14 | 1338 15 | 16 | 4233 17 | 18 | 19 | 7230 20 | 21 | 22 | 5660 23 | 24 | 25 | 10000 26 | 27 | 28 | 1025 29 | 30 | 31 | 8877 32 | 33 | 7700 34 | 35 | 36 | 8448 37 | 38 | 4884 39 | 40 | 41 | 9339 42 | 43 | 9559 44 | 45 | 9669 46 | 47 | 48 | 7997 49 | 7667 50 | 51 | 6776 52 | 53 | 3737 54 | 55 | 1988 56 | 57 | 2015 58 | 59 | 1969 60 | 61 | 3000 62 | 63 | 1964 64 | 65 | 1979 66 | 67 | 1965 68 | 69 | 70 | --- 71 | 72 | 73 | 2468 74 | 8642 75 | 9753 76 | 3579 77 | 3690 78 | 79 | 1121 80 | 2212 81 | 3313 82 | 83 | 9909 84 | 3343 85 | 86 | 8818 87 | 88 | 2311 89 | 90 | 7231 91 | 92 | 93 | 94 | ...oic 95 | we should not have a default port 96 | or rather 97 | the default port should be 80 98 | 99 | 100 | -------------------------------------------------------------------------------- /res/experiments/2015-05-31-file-cache.c: -------------------------------------------------------------------------------- 1 | 2 | typedef struct SLNFileCache *SLNFileCacheRef; 3 | 4 | struct item { 5 | str_t *path; 6 | uv_buf_t buf[1]; 7 | unsigned refcount; 8 | struct item *next; 9 | }; 10 | struct SLNFileCache { 11 | async_mutex_t mutex[1]; 12 | struct item *items; 13 | struct item *head; 14 | struct item *tail; 15 | }; 16 | 17 | // is it even sln? 18 | // or is it just part of the blog system? 19 | 20 | // well the server api could use it 21 | // although not as desperately 22 | 23 | SLNFileCacheRef SLNFileCacheCreate(void); 24 | int SLNFileCacheGet(SLNFileCacheRef const cache, strarg_t const path, struct item **const out); 25 | 26 | // we need reference counting? 27 | 28 | // one simplification... we don't need to be thread-safe 29 | // we only need to send files on the main thread 30 | 31 | // actually at some point it might be nice to support multiple threads 32 | 33 | // one lock for the whole cache (perfect for the single threaded case) 34 | // a linked list to track usage recency? 35 | 36 | // our item struct is pretty bloated 37 | 38 | // what if buffers were detached while used? 39 | // we wouldnt need a refcount 40 | // but they couldnt be shared either, which is unacceptable 41 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /res/experiments/2015-06-21-filter-stream-2.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | // the idea is to make this easier by starting from scratch 4 | 5 | // we can reverse the order of a single batch 6 | // but we can't reverse order across batches 7 | // and the size of a batch is capped at say 50 or 100 items 8 | 9 | // rules 10 | // 1. start with the api 11 | // 2. move everything filter/query related out of slnsession 12 | 13 | typedef struct { 14 | str_t *URI; 15 | uint64_t sortID; 16 | uint64_t fileID; 17 | int dir; 18 | } SLNFilterPosition; 19 | 20 | typedef int (*SLNFilterWriteCB)(void *ctx, uv_buf_t const parts[], unsigned int const count); 21 | 22 | void SLNFilterParseOptions(strarg_t const qs, SLNFilterPosition *const pos, uint64_t *const count, int *const dir); 23 | void SLNFilterPositionCleanup(SLNFilterPosition *const pos); 24 | 25 | int SLNFilterSeekToPosition(SLNFilterRef *const filter, SLNFilterPosition *const pos, DB_txn *const txn); 26 | int SLNFilterGetPosition(SLNFilterRef const filter, SLNFilterPosition *const pos, DB_txn *const txn); 27 | int SLNFilterCopyNextURI(SLNFilterRef *const filter, int const dir, bool const meta, DB_txn *const txn, str_t **const out); 28 | 29 | int SLNFilterCopyURIs(SLNFilterRef const filter, SLNSessionRef const session, SLNFilterPosition *const pos, int const dir, bool const meta, str_t *uris[], size_t *const count); 30 | int SLNFilterWriteURIBatch(SLNFilterRef const filter, SLNSessionRef const session, SLNFilterPosition *const pos, size_t const count, bool const meta, SLNFilterWriteCB const writecb, void *ctx); 31 | int SLNFilterWriteURIs(SLNFilterRef const filter, SLNSessionRef const session, SLNFilterPosition *const pos, uint64_t const count, bool const meta, bool const wait, SLNFilterWriteCB const writecb, void *ctx); 32 | 33 | // something like that...? 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | -------------------------------------------------------------------------------- /res/experiments/2015-07-20-sendfile.c: -------------------------------------------------------------------------------- 1 | 2 | static void poll_cb(uv_poll_t *const handle, int const status, int const events) { 3 | async_switch(handle->data); 4 | } 5 | int async_sendfile(uv_stream_t *const outstream, uv_file const infile, int64_t *const offset, size_t const count) { 6 | int outfd; 7 | rc = uv_fileno((uv_handle_t *)outstream, &outfd); 8 | if(rc < 0) return rc; 9 | 10 | uv_poll_t poll[1]; 11 | poll->data = async_active(); 12 | int rc = uv_poll_init_fd(async_loop, poll, outfd); 13 | if(rc < 0) goto cleanup; 14 | rc = uv_poll_start(poll, UV_WRITABLE, poll_cb); 15 | if(rc < 0) goto cleanup; 16 | async_yield(); 17 | rc = uv_poll_stop(poll); 18 | if(rc < 0) goto cleanup; 19 | 20 | uv_req_t req[1]; 21 | rc = uv_fs_sendfile(async_loop, req, (uv_file)outfd, infile, offset, count, NULL); 22 | 23 | cleanup: 24 | async_close((uv_handle_t *)poll); 25 | return rc; 26 | } 27 | 28 | // okay, wtf 29 | // poll has to happen on the main thread 30 | // sendfile is non-blocking on the network, but blocking on disk io 31 | // so it should happen on the thread pool 32 | 33 | // in theory if the file data is in the buffer cache, it should be non-blocking too 34 | // why cant kernels detect this? 35 | 36 | /* 37 | 38 | file = -1; 39 | for(;;) { 40 | poll until writable 41 | enter pool 42 | open file (first time) 43 | sendfile 44 | leave pool 45 | } 46 | close file 47 | 48 | something like this? 49 | 50 | */ 51 | 52 | 53 | -------------------------------------------------------------------------------- /res/experiments/2015-07-27-test-server.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | var http = require("http"); 4 | 5 | http.createServer(function(req, res) { 6 | res.writeHead(200, { 7 | "Content-Type": "text/plain; charset=utf-8", 8 | "Content-Length": 0, 9 | }); 10 | res.end(); 11 | }).listen(9000, "localhost"); 12 | 13 | -------------------------------------------------------------------------------- /res/experiments/2015-08-15-test.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | void FREE(void **ptrptr) { 4 | free(*ptrptr); *ptrptr = NULL; 5 | } 6 | int main() { 7 | char *x = malloc(100); 8 | FREE(&x); 9 | return 0; 10 | } 11 | 12 | -------------------------------------------------------------------------------- /res/experiments/2015-08-16-tls.c: -------------------------------------------------------------------------------- 1 | 2 | 3 | struct poll_info { 4 | async_t thread; 5 | int res; 6 | int events; 7 | }; 8 | void poll_cb(uv_poll_t *const handle, int const status, int const events) { 9 | struct poll_info *const x = handle->data; 10 | x->status = status; 11 | x->events = events; 12 | async_switch(x->thread); 13 | } 14 | int async_poll(uv_stream_t *const stream, int *const events) { 15 | assert(events); 16 | struct poll_info info[1]; 17 | info->thread = async_active(); 18 | info->res = 0; 19 | info->events = 0; 20 | uv_poll_t handle[1]; 21 | handle->data = info; 22 | 23 | uv_os_fd_t fd; 24 | int rc = uv_fileno((uv_handle_t *)stream, &fd); 25 | if(rc < 0) return rc; 26 | rc = uv_poll_init(async_loop, handle, (uv_os_sock_t)fd); 27 | if(rc < 0) return rc; 28 | rc = uv_poll_start(handle, *events, poll_cb); 29 | if(rc < 0) goto cleanup; 30 | async_yield(); 31 | rc = uv_poll_stop(handle); 32 | cleanup: 33 | async_close((uv_handle_t *)handle); 34 | if(info->res < 0) return info->res; 35 | if(rc < 0) return rc; 36 | *events = info->events; 37 | return 0; 38 | } 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | -------------------------------------------------------------------------------- /res/experiments/2015-08-20-node-keepalive-test.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | var sln = require("/home/user/Code/stronglink/client/node-sln-client/sln-client"); 4 | var repo = sln.repoForName("test"); 5 | 6 | function trampoline(func/* (next) */) { 7 | var called, finished; 8 | for(;;) { 9 | called = false; 10 | finished = false; 11 | func(next); 12 | finished = true; 13 | if(!called) break; 14 | } 15 | function next() { 16 | called = true; 17 | if(finished) trampoline(func); 18 | } 19 | } 20 | 21 | /*process.on("uncaughtException", function(err) { 22 | console.log(err); 23 | });*/ 24 | 25 | repo.query("", { count: 1 }, function(err, URIs) { 26 | if(err) throw err; 27 | var URI = URIs[0]; 28 | trampoline(function(next) { 29 | repo.getFile(URI, {method: "GET"}, function(err, data) { 30 | if(err) throw err; 31 | console.log(new Date); 32 | next(); 33 | }); 34 | }); 35 | }); 36 | 37 | 38 | /*var protocol = require("http"); 39 | var agent = new protocol.Agent({ 40 | keepAlive: true, 41 | maxSockets: 1, 42 | }); 43 | protocol.createServer(function(req, res) { 44 | res.writeHead(200, { 45 | "Content-Length": 4, 46 | "Connection": "keep-alive", 47 | "Content-Type": "text/markdown", 48 | "Cache-Control": "max-age=31536000", 49 | "ETag": "1", 50 | "Content-Security-Policy": "'none'", 51 | "X-Content-Type-Options": "nosniff", 52 | }); 53 | res.end("test", "utf8"); 54 | }).listen(8002); 55 | trampoline(function(next) { 56 | protocol.get({ 57 | hostname: "localhost", 58 | port: 8002, 59 | agent: agent, 60 | }, function(res) { 61 | res.on("data", function() {}); 62 | res.on("end", function() { 63 | console.log(new Date); 64 | next(); 65 | }); 66 | }); 67 | });*/ 68 | 69 | -------------------------------------------------------------------------------- /res/experiments/2015-08-22-io-architecture.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2015-08-22-io-architecture.gif -------------------------------------------------------------------------------- /res/experiments/2015-08-22-io-architecture.odg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/experiments/2015-08-22-io-architecture.odg -------------------------------------------------------------------------------- /res/favicon.xcf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/btrask/stronglink/b6e8d4492832a67ab252ad58017c6254c8c39f79/res/favicon.xcf -------------------------------------------------------------------------------- /src/blog/Blog.h: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include "../StrongLink.h" 9 | #include "Template.h" 10 | 11 | typedef struct Blog* BlogRef; 12 | 13 | #define PENDING_MAX 4 14 | 15 | struct Blog { 16 | SLNRepoRef repo; 17 | 18 | str_t *dir; 19 | str_t *cacheDir; 20 | 21 | TemplateRef header; 22 | TemplateRef footer; 23 | TemplateRef entry_start; 24 | TemplateRef entry_end; 25 | TemplateRef preview; 26 | TemplateRef empty; 27 | TemplateRef compose; 28 | TemplateRef upload; 29 | TemplateRef login; 30 | TemplateRef notfound; 31 | TemplateRef noresults; 32 | 33 | async_mutex_t pending_mutex[1]; 34 | async_cond_t pending_cond[1]; 35 | strarg_t pending[PENDING_MAX]; 36 | }; 37 | 38 | BlogRef BlogCreate(SLNRepoRef const repo); 39 | void BlogFree(BlogRef *const blogptr); 40 | int BlogDispatch(BlogRef const blog, SLNSessionRef const session, HTTPConnectionRef const conn, HTTPMethod const method, strarg_t const URI, HTTPHeadersRef const headers); 41 | 42 | int BlogConvert(BlogRef const blog, 43 | SLNSessionRef const session, 44 | strarg_t const html, 45 | SLNSubmissionRef *const meta, 46 | strarg_t const URI, 47 | SLNFileInfo const *const src); 48 | int BlogGeneric(BlogRef const blog, 49 | SLNSessionRef const session, 50 | strarg_t const htmlpath, 51 | strarg_t const URI, 52 | SLNFileInfo const *const src); 53 | 54 | // TODO: Get rid of this stuff, or refactor it. 55 | typedef struct { 56 | BlogRef blog; 57 | SLNSessionRef session; 58 | strarg_t fileURI; 59 | } preview_state; 60 | extern TemplateArgCBs const preview_cbs; 61 | 62 | -------------------------------------------------------------------------------- /src/blog/RSSServer.h: -------------------------------------------------------------------------------- 1 | // Copyright 2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include "../StrongLink.h" 6 | 7 | typedef struct RSSServer *RSSServerRef; 8 | 9 | int RSSServerCreate(SLNRepoRef const repo, RSSServerRef *const out); 10 | void RSSServerFree(RSSServerRef *const rssptr); 11 | 12 | int RSSServerDispatch(RSSServerRef const rss, SLNSessionRef const session, HTTPConnectionRef const conn, HTTPMethod const method, strarg_t const URI, HTTPHeadersRef const headers); 13 | 14 | -------------------------------------------------------------------------------- /src/blog/Template.h: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | #include "../common.h" 7 | 8 | typedef struct Template* TemplateRef; 9 | 10 | typedef struct { 11 | str_t *(*lookup)(void const *const ctx, strarg_t const var); 12 | void (*free)(void const *const ctx, strarg_t const var, str_t **const val); 13 | } TemplateArgCBs; 14 | 15 | typedef int (*TemplateWritev)(void *, uv_buf_t[], unsigned int); 16 | 17 | int TemplateCreate(strarg_t const str, TemplateRef *const out); 18 | int TemplateCreateFromPath(strarg_t const path, TemplateRef *const out); 19 | void TemplateFree(TemplateRef *const tptr); 20 | int TemplateWrite(TemplateRef const t, TemplateArgCBs const *const cbs, void const *const actx, TemplateWritev const writev, void *wctx); 21 | int TemplateWriteHTTPChunk(TemplateRef const t, TemplateArgCBs const *const cbs, void const *actx, HTTPConnectionRef const conn); 22 | int TemplateWriteFile(TemplateRef const t, TemplateArgCBs const *const cbs, void const *actx, uv_file const file); 23 | 24 | typedef struct { 25 | strarg_t var; 26 | strarg_t val; 27 | } TemplateStaticArg; 28 | extern TemplateArgCBs const TemplateStaticCBs; 29 | 30 | str_t *htmlenc(strarg_t const str); 31 | 32 | -------------------------------------------------------------------------------- /src/blog/plaintext.c: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include "converter.h" 5 | 6 | TYPE_LIST(plaintext, 7 | "text/plain; charset=utf-8", 8 | "text/plain", 9 | SLN_META_TYPE, 10 | "text/x-sln-meta+json; charset=utf-8", // TODO: Get rid of these obsolete types. 11 | "text/efs-meta+json; charset=utf-8") 12 | CONVERTER(plaintext) { 13 | if(size > LIMIT_DEFAULT) return UV_EFBIG; 14 | 15 | yajl_gen_string(json, (unsigned char const *)STR_LEN("link")); 16 | yajl_gen_map_open(json); 17 | 18 | regex_t linkify[1]; 19 | int rc = regcomp(linkify, LINKIFY_RE, REG_ICASE | REG_EXTENDED); 20 | if(0 != rc) return UV_ENOMEM; 21 | 22 | rc = write_html(html, STR_LEN("
"));
23 | 	if(rc < 0) goto cleanup;
24 | 
25 | 	char const *pos = buf;
26 | 	regmatch_t match;
27 | 	while(0 == regexec(linkify, pos, 1, &match, 0)) {
28 | 		regoff_t const loc = match.rm_so;
29 | 		regoff_t const len = match.rm_eo - match.rm_so;
30 | 
31 | 		rc = write_text(html, pos, loc);
32 | 		if(rc < 0) goto cleanup;
33 | 		rc = write_link(html, pos+loc, len);
34 | 		if(rc < 0) goto cleanup;
35 | 
36 | 		yajl_gen_string(json, (unsigned char const *)pos+loc, len);
37 | 		yajl_gen_map_open(json);
38 | 		yajl_gen_map_close(json);
39 | 
40 | 		pos += loc+len;
41 | 	}
42 | 	rc = write_text(html, pos, size-(pos-buf));
43 | 	if(rc < 0) goto cleanup;
44 | 	rc = write_html(html, STR_LEN("
")); 45 | if(rc < 0) goto cleanup; 46 | 47 | yajl_gen_map_close(json); 48 | 49 | yajl_gen_string(json, (unsigned char const *)STR_LEN("fulltext")); 50 | yajl_gen_string(json, (unsigned char const *)buf, size); 51 | 52 | cleanup: 53 | regfree(linkify); 54 | return rc; 55 | } 56 | 57 | -------------------------------------------------------------------------------- /src/util/fts.c: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | #include "fts.h" 7 | 8 | #define thread_local __thread // TODO 9 | 10 | void sqlite3Fts3PorterTokenizerModule( 11 | sqlite3_tokenizer_module const**ppModule 12 | ); 13 | 14 | static thread_local sqlite3_tokenizer_module const *_fts = NULL; 15 | static thread_local sqlite3_tokenizer *_tokenizer = NULL; 16 | 17 | void fts_get(sqlite3_tokenizer_module const **const fts, sqlite3_tokenizer **const tokenizer) { 18 | if(!_fts) { 19 | sqlite3Fts3PorterTokenizerModule(&_fts); 20 | assert(fts); 21 | int rc = _fts->xCreate(0, NULL, &_tokenizer); 22 | assert(SQLITE_OK == rc); 23 | } 24 | *fts = _fts; 25 | *tokenizer = _tokenizer; 26 | } 27 | 28 | -------------------------------------------------------------------------------- /src/util/fts.h: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include "../../deps/fts3/fts3_tokenizer.h" 5 | 6 | void fts_get(sqlite3_tokenizer_module const **const fts, sqlite3_tokenizer **const tokenizer); 7 | 8 | -------------------------------------------------------------------------------- /src/util/libco_coro.c: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | // Good for CORO_USE_VALGRIND. 5 | 6 | #include 7 | #include 8 | #include 9 | #include "../../deps/libco/libco.h" 10 | #include "../../deps/libcoro/coro.h" 11 | 12 | #ifdef LIBCO_MP 13 | #define thread_local __thread 14 | #else 15 | #define thread_local 16 | #endif 17 | 18 | typedef struct { 19 | coro_context context; 20 | struct coro_stack stack; 21 | } coro_thread; 22 | 23 | static thread_local cothread_t _co_active; 24 | 25 | static thread_local int init = 0; 26 | static void co_init(void) { 27 | coro_thread *const t = calloc(1, sizeof(coro_thread)); 28 | assert(t && "libco_coro couldn't init"); 29 | coro_create(&t->context, NULL, NULL, NULL, 0); 30 | _co_active = t; 31 | } 32 | 33 | cothread_t co_active(void) { 34 | if(!init) { 35 | co_init(); 36 | init = 1; 37 | } 38 | return _co_active; 39 | } 40 | cothread_t co_create(unsigned int s, void (*f)(void)) { 41 | if(!init) { 42 | co_init(); 43 | init = 1; 44 | } 45 | coro_thread *const t = malloc(sizeof(coro_thread)); 46 | if(!t) return NULL; 47 | if(!coro_stack_alloc(&t->stack, s / sizeof(void *))) { 48 | free(t); 49 | return NULL; 50 | } 51 | coro_create(&t->context, (void (*)())f, NULL, t->stack.sptr, t->stack.ssze); 52 | return t; 53 | } 54 | void co_delete(cothread_t const thread) { 55 | coro_thread *t = thread; 56 | coro_destroy(&t->context); 57 | coro_stack_free(&t->stack); 58 | free(t); 59 | } 60 | void co_switch(cothread_t const thread) { 61 | coro_thread *const a = _co_active; 62 | coro_thread *const b = thread; 63 | _co_active = thread; 64 | coro_transfer(&a->context, &b->context); 65 | } 66 | 67 | -------------------------------------------------------------------------------- /src/util/pass.c: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | #include "../../deps/crypt_blowfish/ow-crypt.h" 7 | #include 8 | #include "pass.h" 9 | 10 | #define BCRYPT_PREFIX "$2b$" 11 | #define BCRYPT_ROUNDS 13 12 | #define BCRYPT_SALT_LEN 16 13 | 14 | int pass_hashcmp(char const *const pass, char const *const hash) { 15 | async_pool_enter(NULL); 16 | int size = 0; 17 | void *data = NULL; 18 | char const *attempt = crypt_ra(pass, hash, &data, &size); 19 | bool const success = (attempt && 0 == strcmp(attempt, hash)); 20 | attempt = NULL; 21 | free(data); data = NULL; 22 | async_pool_leave(NULL); 23 | if(!success) return -1; 24 | return 0; 25 | } 26 | char *pass_hash(char const *const pass) { 27 | // TODO: async_random isn't currently parallel or thread-safe 28 | // async_pool_enter(NULL); 29 | char input[BCRYPT_SALT_LEN]; 30 | if(async_random((unsigned char *)input, BCRYPT_SALT_LEN) < 0) { 31 | // async_pool_leave(NULL); 32 | return NULL; 33 | } 34 | async_pool_enter(NULL); // TODO (above) 35 | 36 | char *salt = crypt_gensalt_ra(BCRYPT_PREFIX, BCRYPT_ROUNDS, input, BCRYPT_SALT_LEN); 37 | if(!salt) { 38 | async_pool_leave(NULL); 39 | return NULL; 40 | } 41 | int size = 0; 42 | void *data = NULL; 43 | char const *orig = crypt_ra(pass, salt, &data, &size); 44 | char *hash = orig ? strdup(orig) : NULL; 45 | free(salt); salt = NULL; 46 | free(data); data = NULL; 47 | async_pool_leave(NULL); 48 | return hash; 49 | } 50 | 51 | -------------------------------------------------------------------------------- /src/util/pass.h: -------------------------------------------------------------------------------- 1 | // Copyright 2014-2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | 6 | int pass_hashcmp(char const *const pass, char const *const hash); 7 | char *pass_hash(char const *const pass); 8 | 9 | -------------------------------------------------------------------------------- /src/util/strext.c: -------------------------------------------------------------------------------- 1 | // Copyright 2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include "strext.h" 10 | 11 | char *vaasprintf(char const *const fmt, va_list ap) { 12 | va_list ap2; 13 | va_copy(ap2, ap); 14 | int rc = vsnprintf(NULL, 0, fmt, ap2); 15 | va_end(ap2); 16 | if(rc < 0) return NULL; 17 | char *str = malloc(rc+1); 18 | if(!str) return NULL; 19 | rc = vsnprintf(str, rc+1, fmt, ap); 20 | if(rc < 0) { 21 | free(str); 22 | return NULL; 23 | } 24 | return str; 25 | } 26 | char *aasprintf(char const *const fmt, ...) { 27 | va_list ap; 28 | va_start(ap, fmt); 29 | char *str = vaasprintf(fmt, ap); 30 | va_end(ap); 31 | return str; 32 | } 33 | 34 | int time_iso8601(char *const out, size_t const max) { 35 | assert(max > 0); 36 | time_t const now = time(NULL); 37 | struct tm t[1]; 38 | gmtime_r(&now, t); // TODO: Error checking? 39 | size_t len = strftime(out, max, "%FT%TZ", t); 40 | if(0 == len) return -1; 41 | return 0; 42 | } 43 | void valogf(char const *const fmt, va_list ap) { 44 | async_pool_enter(NULL); 45 | char t[31+1]; 46 | int rc = time_iso8601(t, sizeof(t)); 47 | assert(rc >= 0); 48 | flockfile(stderr); 49 | fprintf(stderr, "%s ", t); 50 | vfprintf(stderr, fmt, ap); 51 | funlockfile(stderr); 52 | async_pool_leave(NULL); 53 | } 54 | void alogf(char const *const fmt, ...) { 55 | va_list ap; 56 | va_start(ap, fmt); 57 | valogf(fmt, ap); 58 | va_end(ap); 59 | } 60 | 61 | int uripathcmp(char const *const literal, char const *const input, char const **const qs) { 62 | size_t const len = strlen(literal); 63 | assert(len); 64 | if(0 != strncmp(literal, input, len)) return -1; 65 | // We don't ignore trailing / because it's significant. 66 | if('\0' != input[len] && '?' != input[len]) return -1; 67 | if(qs) *qs = input+len; 68 | return 0; 69 | } 70 | 71 | -------------------------------------------------------------------------------- /src/util/strext.h: -------------------------------------------------------------------------------- 1 | // Copyright 2015 Ben Trask 2 | // MIT licensed (see LICENSE for details) 3 | 4 | #include 5 | #include 6 | 7 | char *vaasprintf(char const *const fmt, va_list ap) __attribute__((format(printf, 1, 0))); 8 | char *aasprintf(char const *const fmt, ...) __attribute__((format(printf, 1, 2))); 9 | 10 | int time_iso8601(char *const out, size_t const max); 11 | 12 | void valogf(char const *const fmt, va_list ap) __attribute__((format(printf, 1, 0))); 13 | void alogf(char const *const fmt, ...) __attribute__((format(printf, 1, 2))); 14 | 15 | int uripathcmp(char const *const literal, char const *const input, char const **const qs); 16 | 17 | --------------------------------------------------------------------------------