{"id":16877672,"url":"https://github.com/nikic/sample_prof","last_synced_at":"2025-03-22T07:31:58.894Z","repository":{"id":11751353,"uuid":"14282272","full_name":"nikic/sample_prof","owner":"nikic","description":"Sampling profiler for PHP","archived":false,"fork":false,"pushed_at":"2023-05-31T19:38:38.000Z","size":26,"stargazers_count":59,"open_issues_count":4,"forks_count":6,"subscribers_count":5,"default_branch":"master","last_synced_at":"2025-03-18T09:21:55.441Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"C","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"other","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/nikic.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}},"created_at":"2013-11-10T19:05:50.000Z","updated_at":"2024-07-03T15:40:38.000Z","dependencies_parsed_at":"2024-10-28T12:30:40.860Z","dependency_job_id":"75e24381-3a4b-4bca-b233-f2b485fff221","html_url":"https://github.com/nikic/sample_prof","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nikic%2Fsample_prof","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nikic%2Fsample_prof/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nikic%2Fsample_prof/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nikic%2Fsample_prof/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/nikic","download_url":"https://codeload.github.com/nikic/sample_prof/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":244925178,"owners_count":20532873,"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","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":[],"created_at":"2024-10-13T15:44:48.339Z","updated_at":"2025-03-22T07:31:58.645Z","avatar_url":"https://github.com/nikic.png","language":"C","funding_links":[],"categories":[],"sub_categories":[],"readme":"Sampling profiler for PHP\n=========================\n\nThis project implements a basic sampling profiler for PHP.\n\nMost (all?) other profilers for PHP work by hooking into function execution (`zend_execute_ex`\nto be more precise). This means that\n\n * they only provide resolution on the function call level, but don't specify which lines in a\n   function took the longest to run.\n * they slow down code execution significantly and asymmetrically, which often also impacts which\n   parts are slowest. Thus the profiler may tell you something is slow, but it's not actually slow\n   in a production environment (with profiling disabled).\n\nA sampling profiler on the other hand provides line-level resolution and, depending on the chosen\nsampling interval, either doesn't affect performance at all or slows down everything symmetrically.\n\nInstallation\n------------\n\nIn the directory of the extension run:\n\n    phpize\n    ./configure\n    make\n    sudo make install\n\nUsage\n-----\n\n### API\n\n#### `void sample_prof_start($interval_usec = 1, $num_entries_alloc = 1\u003c\u003c20)`\n\nStarts the profiler. Parameters:\n\n * `$interval_usec`: Sampling interval in microseconds. The smaller this parameter is, the more\n   samples will be collected, the more accurate the result will be. At the same time a smaller\n   value for this parameter will increase the performance impact. A value of `1000` has virtually\n   no impact on performance whereas a value of `10` causes approximately 20% performance\n   regression (for me at least, this will probably heavily depend on your machine). Very low\n   values (like `1`) will likely cause massive performance regressions (many times slower) and may\n   be subject to artifacts caused by queued signals. As such setting it to the lowest possible\n   value is probably not a good idea and it's suggested to stay somewhere on the 1000-10 range.\n\n * `$num_entries_alloc`: The number of profiling entries to allocate. As it's not possible to\n   perform allocations within a signal handler all used memory needs to be preallocated. If the\n   number of samples reaches `$num_entries_alloc` no further samples will be collected. The default\n   of `1 \u003c\u003c 20` corresponds to roughly one million samples (the actual allocation size being 8MB or\n   16MB depending on platform). At a sampling interval of 100usec this will allow sampling to\n   continue for approximately 100 seconds.\n\n#### `bool sample_prof_end()`\n\nEnds collection of samples. Returns `true` is the profiler was running at the time of the call\nor `false` otherwise. This information is useful if you want to find out whether the number of\nsamples exceeded `$num_entries_alloc` and the profiler was automatically disabled because of that.\n\n#### `array sample_prof_get_data()`\n\nRetrieves the profiling data as an array with format `[$file =\u003e [$line =\u003e $hits]]`, which specifies\nhow often a certain line in a certain file was hit during sampling. The hits are *not* cumulative,\ni.e. hits that happen in a function call will not be added to the line of the function call.\n\n#### Example usage\n\n```php\n\u003c?php\n\nsample_prof_start(50);          // start profiler with 50 usec interval\nrequire $script;                // run script here\nsample_prof_end();              // disable profiler\n$data = sample_prof_get_data(); // retrieve profiling data\n\nforeach ($data as $file =\u003e $lines) {\n    echo \"In file $file:\\n\";\n    foreach ($lines as $line =\u003e $hits) {\n        echo \"Line $line hit $hits times.\\n\";\n    }\n}\n```\n\n### Script\n\nA `sample_prof.php` script is provided for convenience. It is invoked as follows:\n\n    php sample_prof.php [--html | --callgrind] [--interval=usec] script.php [...args] \u003e out\n\n`sample_prof.php` will run the script `script.php` with the passed `...args` and profile the\nexecution. The output format is specified using `--html` (default) or `--callgrind`. The former\nwill output HTML which can be viewed in a browser of your choice, while the latter produces a\ncallgrind output which you can view in a tool like KCacheGrind. You can adjust the sampling\ninterval using the `--interval` option.\n\nIt is recommended to let `script.php` run multiple seconds to get good statistical coverage. The\nlonger the script runs the better the results will be.\n\n[Sample profiling output][sample_output]: The numbers in the second column specify how often a\nline has been hit. Lines that were hit more often are displayed in red.\n\nNote that the hits are *not cumulative*, i.e. if you perform a function the hits within the call\nwill *not* be added to the hits on the function call line.\n\nTodo\n----\n\n * Maybe support profiling in multi-threaded environments.\n * Check whether we can get cumulative hits without impacting performance too much.\n * Check whether we can avoid getting incorrect results when the `SIGPROF` interrupt handler is\n   invoked at a time where `active_op_array` has already been changed but `opline_ptr` is not\n   updated yet.\n\n  [sample_output]: http://i.imgur.com/FAID0VC.png\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnikic%2Fsample_prof","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnikic%2Fsample_prof","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnikic%2Fsample_prof/lists"}