{"id":23734295,"url":"https://github.com/sailormoon/stopwatch","last_synced_at":"2025-09-04T09:33:32.542Z","repository":{"id":76725404,"uuid":"86949699","full_name":"sailormoon/stopwatch","owner":"sailormoon","description":"⏱️ Single-header C++11 RDTSCP clock and timing utilities released into the public domain.","archived":false,"fork":false,"pushed_at":"2019-04-20T03:40:47.000Z","size":7,"stargazers_count":110,"open_issues_count":0,"forks_count":20,"subscribers_count":10,"default_branch":"master","last_synced_at":"2025-06-04T22:03:33.386Z","etag":null,"topics":["c-plus-plus","header-only","modern","rdtscp","simple","stopwatch","time","timer"],"latest_commit_sha":null,"homepage":"","language":"C++","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"unlicense","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/sailormoon.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2017-04-01T23:40:42.000Z","updated_at":"2024-10-22T16:42:55.000Z","dependencies_parsed_at":"2023-03-01T20:00:47.707Z","dependency_job_id":null,"html_url":"https://github.com/sailormoon/stopwatch","commit_stats":null,"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/sailormoon/stopwatch","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sailormoon%2Fstopwatch","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sailormoon%2Fstopwatch/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sailormoon%2Fstopwatch/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sailormoon%2Fstopwatch/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/sailormoon","download_url":"https://codeload.github.com/sailormoon/stopwatch/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/sailormoon%2Fstopwatch/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":273583440,"owners_count":25131831,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-09-04T02:00:08.968Z","response_time":61,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["c-plus-plus","header-only","modern","rdtscp","simple","stopwatch","time","timer"],"created_at":"2024-12-31T05:45:16.143Z","updated_at":"2025-09-04T09:33:32.508Z","avatar_url":"https://github.com/sailormoon.png","language":"C++","funding_links":[],"categories":[],"sub_categories":[],"readme":"# ⏱️ stopwatch\nSingle-header C++11 RDTSCP clock and timing utilities released into the public domain.\n\n# why\nWhile developing games, I have wanted the following features which are not provided by `std::chrono`:\n1. triggering events after a certain amount of time\n2. timing function calls in a high precision manner\n\n# requirements\n1. The `RDTSCP` instruction and a compiler which supports C++11 or higher.\n2. Your processor must have an [Intel Nehalem (2008)](https://en.wikipedia.org/wiki/Nehalem_(microarchitecture)) or newer processor _or_ a processeor with an invariant TSC.\n\nIf you do not meet these requirements, you can easily remove the `RDTSCP` code from the library and enjoy the other features. The relevant sections of the [The Intel Software Developer Manuals](http://www.intel.com/Assets/en_US/PDF/manual/253668.pdf) are at the bottom of this page.\n\n# usage\n## timer\n```c++\n#include \"stopwatch.h\"\n#include \u003cchrono\u003e\n#include \u003ciostream\u003e\n#include \u003cthread\u003e\n\nint main() {\n  const auto timer = stopwatch::make_timer(std::chrono::seconds(10));\n  while (!timer.done()) {\n    std::cout \u003c\u003c std::chrono::duration_cast\u003cstd::chrono::seconds\u003e(\n                     timer.remaining())\n                     .count()\n              \u003c\u003c \" seconds remain.\" \u003c\u003c std::endl;\n    std::this_thread::sleep_for(std::chrono::milliseconds(100));\n  }\n  std::cout \u003c\u003c \"10 seconds have elapsed\" \u003c\u003c std::endl;\n}\n```\n\n## timing one function call\n```c++\n#include \"stopwatch.h\"\n#include \u003ciostream\u003e\n\nint main() {\n  const auto cycles = stopwatch::time([] {\n    for (std::size_t i = 0; i \u003c 10; ++i) {\n      std::cout \u003c\u003c i \u003c\u003c std::endl;\n    }\n  });\n\n  std::cout \u003c\u003c \"To print out 10 numbers, it took \" \u003c\u003c cycles.count()\n            \u003c\u003c \" cycles.\" \u003c\u003c std::endl;\n}\n```\n\n## sampling multiple calls to a function\nTaking the median number of cycles for inserting 10000 items into the beginning of a container.\n```c++\n#include \"stopwatch.h\"\n#include \u003cdeque\u003e\n#include \u003ciostream\u003e\n#include \u003cvector\u003e\n\nint main() {\n  const auto deque_samples = stopwatch::sample\u003c100\u003e([] {\n    std::deque\u003cint\u003e deque;\n    for (std::size_t i = 0; i \u003c 10000; ++i) {\n      deque.insert(deque.begin(), i);\n    }\n  });\n\n  const auto vector_samples = stopwatch::sample\u003c100\u003e([] {\n    std::vector\u003cint\u003e vector;\n    for (std::size_t i = 0; i \u003c 10000; ++i) {\n      vector.insert(vector.begin(), i);\n    }\n  });\n\n  std::cout \u003c\u003c \"median for deque: \" \u003c\u003c deque_samples[49].count() \u003c\u003c std::endl;\n  std::cout \u003c\u003c \"median for vector: \" \u003c\u003c vector_samples[49].count() \u003c\u003c std::endl;\n}\n```\n\nOutput on my MacbookPro 2016:\n```\nmedian for deque:   487760\nmedian for vector: 7595754\n```\n\n# using another clock\nUsing another clock is as simple as passing the clock in as a template argument. An example using `std::chrono::system_clock` inplace of `stopwatch::rdtscp_clock` for the `timing one function call` example:\n```c++\n  const auto cycles = stopwatch::time\u003cstd::chrono::system_clock\u003e([] {\n    for (std::size_t i = 0; i \u003c 10; ++i) {\n      std::cout \u003c\u003c i \u003c\u003c std::endl;\n    }\n  });\n```\n`stopwatch::time([] { ... })` became `stopwatch::time\u003cstd::chrono::system_clock\u003e([] { ... }`. That's it!\n\n# contributing\nContributions of any variety are greatly appreciated. All code is passed through `clang-format` using the Google style.\n\n## [The Intel Software Developer Manuals](http://www.intel.com/Assets/en_US/PDF/manual/253668.pdf)\n### Section 16.12.1\n\u003e The time stamp counter in newer processors may support an enhancement, referred\nto as invariant TSC. Processor’s support for invariant TSC is indicated by\nCPUID.80000007H:EDX[8].\nThe invariant TSC will run at a constant rate in all ACPI P-, C-. and T-states. This is\nthe architectural behavior moving forward. On processors with invariant TSC\nsupport, the OS may use the TSC for wall clock timer services (instead of ACPI or\nHPET timers). TSC reads are much more efficient and do not incur the overhead\nassociated with a ring transition or access to a platform resource.\n\n### Section 16.12.2\n\u003e Processors based on Intel microarchitecture code name Nehalem provide an auxiliary\nTSC register, IA32_TSC_AUX that is designed to be used in conjunction with\nIA32_TSC. IA32_TSC_AUX provides a 32-bit field that is initialized by privileged software\nwith a signature value (for example, a logical processor ID).\n\n\u003e The primary usage of IA32_TSC_AUX in conjunction with IA32_TSC is to allow software\nto read the 64-bit time stamp in IA32_TSC and signature value in\nIA32_TSC_AUX with the instruction RDTSCP in an atomic operation. RDTSCP returns\nthe 64-bit time stamp in EDX:EAX and the 32-bit TSC_AUX signature value in ECX.\nThe atomicity of RDTSCP ensures that no context switch can occur between the reads\nof the TSC and TSC_AUX values.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsailormoon%2Fstopwatch","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsailormoon%2Fstopwatch","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsailormoon%2Fstopwatch/lists"}