{"id":330858,"date":"2022-03-20T15:00:27","date_gmt":"2022-03-20T15:00:27","guid":{"rendered":"http:\/\/savepearlharbor.com\/?p=330858"},"modified":"-0001-11-30T00:00:00","modified_gmt":"-0001-11-29T21:00:00","slug":"","status":"publish","type":"post","link":"https:\/\/savepearlharbor.com\/?p=330858","title":{"rendered":"<span>\u0413\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0443 \u0434\u043b\u044f FMOD<\/span>"},"content":{"rendered":"<div><\/div>\n<div id=\"post-content-body\">\n<div>\n<div class=\"article-formatted-body article-formatted-body_version-2\">\n<div xmlns=\"http:\/\/www.w3.org\/1999\/xhtml\">\n<p>\u041e\u0431\u0451\u0440\u0442\u043a\u0443 \u043c\u043e\u0436\u043d\u043e \u043d\u0430\u043f\u0438\u0441\u0430\u0442\u044c \u0432\u0440\u0443\u0447\u043d\u0443\u044e, \u043a\u043e\u0433\u0434\u0430 API \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0438\u0437 \u043d\u0435\u0431\u043e\u043b\u044c\u0448\u043e\u0433\u043e \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438 \u0441\u0438\u0433\u043d\u0430\u0442\u0443\u0440\u0430 \u044d\u0442\u0438\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u043c\u0435\u043d\u044f\u0435\u0442\u0441\u044f \u043d\u0435\u0447\u0430\u0441\u0442\u043e. FMOD \u2014 \u0437\u0432\u0443\u043a\u043e\u0432\u043e\u0439 \u0434\u0432\u0438\u0436\u043e\u043a \u0441 \u0431\u043e\u043b\u044c\u0448\u0438\u043c \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e\u043c \u0444\u0443\u043d\u043a\u0446\u0438\u0439, \u0442\u043e\u0447\u043d\u043e \u043d\u0435 \u0442\u043e\u0442 \u0441\u043b\u0443\u0447\u0430\u0439:<\/p>\n<pre><code class=\"css\">Types: 19 Callbacks: 96 Structures: 57 Structure Fields: 352 Enumerations: 77 Enumeration Variants: 693 Functions: 573 Function Arguments: 1590<\/code><\/pre>\n<p>\u0421\u0442\u043e\u0438\u043c\u043e\u0441\u0442\u044c \u0440\u0443\u0447\u043d\u043e\u0439 \u0440\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u0434\u043b\u044f \u0442\u0430\u043a\u043e\u0433\u043e API \u0431\u0443\u0434\u0435\u0442 \u0432\u044b\u0441\u043e\u043a\u043e\u0439, \u043f\u043e\u0434\u0434\u0435\u0440\u0436\u043a\u0430 \u043f\u0440\u0438 \u043a\u0430\u0436\u0434\u043e\u043c \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0438 \u043c\u0443\u0447\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0439, \u043d\u0435 \u0433\u043e\u0432\u043e\u0440\u044f \u0443\u0436\u0435 \u043e\u0431 \u043e\u0448\u0438\u0431\u043a\u0430\u0445 \u0438 \u043e\u043f\u0435\u0447\u0430\u0442\u043a\u0430\u0445, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043f\u043e\u044f\u0432\u044f\u0442\u0441\u044f \u0432 \u043f\u0440\u043e\u0446\u0435\u0441\u0441\u0435 \u0440\u0435\u0434\u0430\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f.<\/p>\n<p>\u041a \u0441\u0447\u0430\u0441\u0442\u044c\u044e, FMOD \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438 \u043f\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0432\u043c\u0435\u0441\u0442\u0435 \u0441 \u0445\u043e\u0440\u043e\u0448\u043e \u043e\u0444\u043e\u0440\u043c\u043b\u0435\u043d\u043d\u044b\u043c\u0438 \u0444\u0430\u0439\u043b\u0430\u043c\u0438 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435  \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0434\u043b\u044f \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u043e\u0433\u043e \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u043e\u0431\u0451\u0440\u0442\u043a\u0438.<\/p>\n<p>\u0412 \u044d\u043a\u043e\u0441\u0438\u0441\u0442\u0435\u043c\u0435 Rust \u043d\u0430\u0438\u0431\u043e\u043b\u0435\u0435 \u043f\u043e\u043f\u0443\u043b\u044f\u0440\u043d\u044b\u043c \u0438\u043d\u0441\u0442\u0440\u0443\u043c\u0435\u043d\u0442\u043e\u043c \u044f\u0432\u043b\u044f\u0435\u0442\u0441\u044f <a href=\"https:\/\/rust-lang.github.io\/rust-bindgen\/\" rel=\"noopener noreferrer nofollow\">bindgen<\/a> \u2014 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0430, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u0442 Rust \u043a\u043e\u0434 \u043d\u0430 \u043e\u0441\u043d\u043e\u0432\u0435 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0445 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 C. \u041d\u043e \u0438\u043d\u0441\u0442\u0440\u0443\u043c\u0435\u043d\u0442 \u043d\u0435 \u0438\u0434\u0435\u0430\u043b\u044c\u043d\u044b\u0439, \u043f\u043e \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u0438\u043c \u043f\u0440\u0438\u0447\u0438\u043d\u0430\u043c:<\/p>\n<ul>\n<li>\n<p>Bindgen \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u0442 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0442\u0438\u043f\u043e\u0432 \u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f FFI, \u043d\u043e \u043d\u0430 \u043c\u0438\u043d\u0438\u043c\u0430\u043b\u044c\u043d\u043e \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u043c \u0443\u0440\u043e\u0432\u043d\u0435, \u0441 \u0441\u044b\u0440\u044b\u043c\u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f\u043c\u0438 \u0438 unsafe \u0431\u043b\u043e\u043a\u0430\u043c\u0438 \u044f\u0437\u044b\u043a\u0430, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u044d\u0442\u043e \u0432 \u0438\u0434\u0438\u043e\u043c\u0430\u0442\u0438\u0447\u043d\u043e\u043c Rust \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0438 \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0430\u0442\u0438\u0447\u043d\u043e<\/p>\n<\/li>\n<li>\n<p>\u041f\u043e\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442 \u0432\u0441\u0435 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u0438 \u044f\u0437\u044b\u043a\u0430 C \u043d\u043e \u043d\u0435 \u0443\u0447\u0438\u0442\u044b\u0432\u0430\u0435\u0442 \u043a\u043e\u043d\u0442\u0435\u043a\u0441\u0442 \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u043e\u0433\u043e API, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u043d\u0435 \u0440\u0430\u0437\u0431\u0435\u0440\u0451\u0442: \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438, \u043c\u0430\u043a\u0440\u043e\u0441\u044b \u0441 \u043f\u0440\u0435\u0434\u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043b\u0435\u043d\u043d\u044b\u043c\u0438 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f\u043c\u0438, \u043c\u0430\u043f\u043f\u0438\u043d\u0433 \u043e\u0448\u0438\u0431\u043e\u043a<\/p>\n<\/li>\n<li>\n<p>\u0422\u0440\u0435\u0431\u0443\u0435\u0442 \u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043a\u0438 LLVM \u0441 libclang \u0432 \u043a\u043e\u043c\u043f\u043b\u0435\u043a\u0442\u0435, \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u043e\u0439 \u043d\u0430 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u043f\u043b\u0430\u0442\u0444\u043e\u0440\u043c\u0430\u0445, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 Windows<\/p>\n<\/li>\n<\/ul>\n<p>\u0412\u043c\u0435\u0441\u0442\u043e bindgen, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435 \u0440\u0435\u0448\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0438\u0437 \u0442\u0440\u0435\u0445 \u0448\u0430\u0433\u043e\u0432:<\/p>\n<ol>\n<li>\n<p>\u0420\u0430\u0437\u0431\u043e\u0440 API \u0438\u0437 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 \u0432 \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435<\/p>\n<\/li>\n<li>\n<p>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u043a\u043e\u0434\u0430 FFI \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0439<\/p>\n<\/li>\n<li>\n<p>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u043a\u043e\u0434\u0430 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438<\/p>\n<\/li>\n<\/ol>\n<h2>\u0420\u0430\u0437\u0431\u043e\u0440 API<\/h2>\n<p>\u0414\u043b\u044f \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 FMOD \u0431\u0443\u0434\u0435\u043c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0430\u0440\u0441\u0435\u0440 \u043e\u0431\u0449\u0435\u0433\u043e \u043d\u0430\u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f <a href=\"https:\/\/pest.rs\" rel=\"noopener noreferrer nofollow\">pest<\/a>. \u041f\u0430\u0440\u0441\u0435\u0440 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438 <a href=\"https:\/\/en.wikipedia.org\/wiki\/Parsing_expression_grammar\" rel=\"noopener noreferrer nofollow\">PEG<\/a>, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0430\u043d\u0430\u043b\u043e\u0433\u0438\u0447\u043d\u044b \u0440\u0435\u0433\u0443\u043b\u044f\u0440\u043d\u044b\u043c \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c, \u043d\u043e \u0434\u0430\u044e\u0442 \u0431\u043e\u043b\u044c\u0448\u0435 \u0432\u044b\u0440\u0430\u0437\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438, \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u0439 \u0434\u043b\u044f \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u043b\u043e\u0436\u043d\u044b\u0445 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0446\u0438\u0439.<\/p>\n<p>\u041f\u0440\u043e\u0441\u0442\u043e\u0439 \u043f\u0440\u0438\u043c\u0435\u0440 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438 \u0434\u043b\u044f \u0441\u043f\u0438\u0441\u043a\u0430 \u0431\u0443\u043a\u0432\u0435\u043d\u043d\u043e-\u0446\u0438\u0444\u0440\u043e\u0432\u044b\u0445 \u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440\u043e\u0432:<\/p>\n<pre><code class=\"rust\">alpha = { 'a'..'z' | 'A'..'Z' } digit = { '0'..'9' } ident = { (alpha | digit)+ }<\/code><\/pre>\n<p>\u0422\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c \u043d\u0430\u043f\u0438\u0448\u0435\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0434\u043b\u044f \u0432\u0441\u0435\u0445 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0439 \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432. \u041f\u043e\u043b\u043d\u044b\u0439 \u0440\u0430\u0437\u0431\u043e\u0440 \u044f\u0437\u044b\u043a\u0430 C \u0434\u0435\u043b\u0430\u0442\u044c \u043d\u0435 \u043d\u0443\u0436\u043d\u043e, \u0442\u043e\u043b\u044c\u043a\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c\u044b\u0435 \u0430\u0431\u0441\u0442\u0440\u0430\u043a\u0446\u0438\u0438 \u0438 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u043d\u044b\u0435 \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u044b FMOD. \u042d\u0442\u043e \u0441\u043e\u043a\u0440\u0430\u0449\u0430\u0435\u0442 \u0432\u0440\u0435\u043c\u044f \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u0438.<\/p>\n<pre><code class=\"rust\">declaration = _{ Function | Directive | ExternLinkage } API = { SOI ~ declaration* ~ EOI  }<\/code><\/pre>\n<p>\u0422\u0438\u043f\u0430\u0436 <code>Parser<\/code> \u2014 \u044f\u0434\u0440\u043e pest, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0434\u043b\u044f \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u043e\u0433\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430. \u0420\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u044b\u0432\u0430\u0442\u044c \u0432\u0440\u0443\u0447\u043d\u0443\u044e \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043d\u0435 \u043d\u0443\u0436\u043d\u043e, \u043c\u0430\u043a\u0440\u043e\u0441 \u0438\u0437 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438 <code>pest_derive<\/code> \u043c\u043e\u0436\u0435\u0442 \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u0438 \u0441\u0433\u0435\u043d\u0435\u0440\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u043a\u043e\u0434 \u0438\u0437 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438:<\/p>\n<pre><code class=\"rust\">#[derive(Parser)] #[grammar = \".\/grammars\/fmod.pest\"] struct FmodParser;<\/code><\/pre>\n<p>\u041f\u043e\u043b\u0443\u0447\u0435\u043d\u0438\u0435 \u0434\u0430\u043d\u043d\u044b\u0445 \u0434\u043b\u044f \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u0441\u0432\u043e\u0434\u0438\u0442\u0441\u044f \u043a \u043f\u0435\u0440\u0435\u0431\u043e\u0440\u0443 \u0438 \u0438\u043d\u0442\u0435\u0440\u043f\u0440\u0435\u0442\u0430\u0446\u0438\u0438 \u043f\u0440\u0430\u0432\u0438\u043b \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0445 \u0432 \u044d\u0442\u0438\u0445 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0430\u0445:<\/p>\n<pre><code class=\"rust\">pub struct Header {     pub functions: Vec&lt;Function>, }  pub fn parse(source: &amp;str) -> Result&lt;Header, Error> {   let mut header = Header::default();      let declarations = FmodParser::parse(Rule::API, source)?         .next()         .ok_or(Error::FileMalformed)?;      for declaration in declarations.into_inner() {         match declaration.as_rule() {             Rule::Function => header.add_function(declaration),             Rule::Directive => ...,             Rule::ExternLinkage => ...,         }     }      Ok(header) }<\/code><\/pre>\n<h3>\u041d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u044b\u0435 \u0442\u0438\u043f\u044b<\/h3>\n<p>\u0412\u0441\u0435 \u043e\u0431\u044a\u0435\u043a\u0442\u044b FMOD \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442\u0441\u044f \u0432 \u0432\u0438\u0434\u0435 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f \u043d\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443. \u042d\u0442\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430 \u043d\u0430\u0437\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u201c\u043d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u043e\u0439\u201d \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u0441\u043a\u0440\u044b\u0432\u0430\u0435\u0442 \u0434\u0435\u0442\u0430\u043b\u0438 \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u0438, \u0431\u0443\u0434\u044c \u0442\u043e \u0434\u0435\u0441\u043a\u0440\u0438\u043f\u0442\u043e\u0440 \u0438\u043b\u0438 \u043f\u0440\u044f\u043c\u043e\u0439 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0430 \u043e\u0431\u044a\u0435\u043a\u0442. \u0414\u043b\u044f \u043e\u0431\u043e\u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0438\u043c\u0435\u043d\u0438 \u0442\u0438\u043f\u0430 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f <code>typedef<\/code>, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440:<\/p>\n<pre><code class=\"cpp\">typedef struct FMOD_SYSTEM         FMOD_SYSTEM; typedef struct FMOD_SOUND          FMOD_SOUND; typedef struct FMOD_CHANNEL        FMOD_CHANNEL;<\/code><\/pre>\n<p>\u0413\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u043e\u0441\u0442\u043e\u044f\u0442 \u0438\u0437 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0439. \u042d\u0442\u0438 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u044f\u044e\u0442 \u0441\u043e\u0431\u043e\u0439 \u0444\u043e\u0440\u043c\u0430\u043b\u044c\u043d\u043e\u0435 \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0438\u044f \u0441\u0442\u0440\u043e\u043a\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044e. \u0412\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f \u043c\u043e\u0436\u043d\u043e \u043a\u043e\u043c\u043f\u043e\u043d\u043e\u0432\u0430\u0442\u044c \u0438\u0437 \u0434\u0440\u0443\u0433\u0438\u0445 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0439, \u0432\u043a\u043b\u0430\u0434\u044b\u0432\u0430\u0442\u044c \u0434\u0440\u0443\u0433 \u0432 \u0434\u0440\u0443\u0433\u0430.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u0432\u044b\u0431\u043e\u0440\u0430 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>|<\/code>. \u041f\u0430\u0440\u0441\u0435\u0440 \u0432\u044b\u0431\u0438\u0440\u0430\u0435\u0442 \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u043c \u043f\u043e\u0440\u044f\u0434\u043a\u0435 \u043f\u0435\u0440\u0432\u043e\u0435 \u0443\u0441\u043f\u0435\u0448\u043d\u043e\u0435 \u0441\u043e\u043f\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>~<\/code>. \u041e\u043d \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0441\u0442\u0440\u043e\u043a\u0430 \u0434\u043e\u043b\u0436\u043d\u0430 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u043e\u0432\u0430\u0442\u044c \u0432\u0441\u0435\u043c \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u043c \u043f\u043e\u0440\u044f\u0434\u043a\u0435.<\/p>\n<p>\u0420\u0443\u0447\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u043f\u0440\u043e\u0431\u0435\u043b\u043e\u0432 \u0438 \u043e\u0442\u0441\u0442\u0443\u043f\u043e\u0432 \u0437\u0430\u0442\u0440\u0443\u0434\u043d\u044f\u0435\u0442 \u0447\u0442\u0435\u043d\u0438\u0435 \u0438 \u0440\u0435\u0434\u0430\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a. \u0415\u0441\u043b\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0441\u043f\u0435\u0446\u0438\u0430\u043b\u044c\u043d\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e <code>WHITESPACE<\/code>, \u043e\u043d\u043e \u0431\u0443\u0434\u0435\u0442 \u043e\u0431\u0440\u0430\u0431\u0430\u0442\u044b\u0432\u0430\u0442\u044c\u0441\u044f \u043d\u0435\u044f\u0432\u043d\u043e \u043c\u0435\u0436\u0434\u0443 \u0434\u0440\u0443\u0433\u0438\u043c\u0438 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c\u0438.<\/p>\n<p>\u0418\u043c\u044f \u0442\u0438\u043f\u0430 \u0432\u043a\u043b\u044e\u0447\u0430\u0435\u0442 \u0446\u0438\u0444\u0440\u044b, \u0430\u043d\u0433\u043b\u0438\u0439\u0441\u043a\u0438\u0435 \u0431\u0443\u043a\u0432\u044b \u0438 \u0441\u0438\u043c\u0432\u043e\u043b\u044b \u043f\u043e\u0434\u0447\u0435\u0440\u043a\u0438\u0432\u0430\u043d\u0438\u044f. \u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>+<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u0447\u0442\u043e \u0438\u043c\u044f \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0445\u043e\u0442\u044f \u0431\u044b \u0438\u0437 \u043e\u0434\u043d\u043e\u0433\u043e \u0441\u0438\u043c\u0432\u043e\u043b\u0430. \u041c\u0435\u0436\u0434\u0443 \u044d\u0442\u0438\u043c\u0438 \u0441\u0438\u043c\u0432\u043e\u043b\u0430\u043c\u0438 \u043d\u0435 \u0434\u043e\u043b\u0436\u043d\u043e \u0431\u044b\u0442\u044c \u043f\u0440\u043e\u0431\u0435\u043b\u043e\u0432, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u043e\u0442\u043c\u0435\u0447\u0435\u043d\u043e \u043a\u0430\u043a \u0430\u0442\u043e\u043c\u0430\u0440\u043d\u043e\u0435 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>@<\/code>.<\/p>\n<pre><code class=\"rust\">WHITESPACE = _{ \" \" | \"\\\\t\" }  name = @{ (\"_\" | ASCII_ALPHANUMERIC)+ }  OpaqueType = { \"typedef\" ~ \"struct\" ~ name ~ name ~ \";\"}<\/code><\/pre>\n<h3>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f<\/h3>\n<p>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0435 \u2014 \u044d\u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c\u044b\u0439 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0442\u0438\u043f, \u0441\u043e\u0441\u0442\u043e\u044f\u0449\u0438\u0439 \u0438\u0437 \u043d\u0430\u0431\u043e\u0440\u0430 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u044b\u0445 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442. \u041f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 C \u044d\u0442\u0438 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u044b \u043d\u0430\u0437\u044b\u0432\u0430\u044e\u0442\u0441\u044f &#171;\u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f\u043c\u0438\u201d. \u0412\u043e\u0437\u043c\u043e\u0436\u043d\u043e \u044f\u0432\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f, \u043a\u0430\u043a \u043f\u043e\u043a\u0430\u0437\u0430\u043d\u043e \u0437\u0434\u0435\u0441\u044c:<\/p>\n<pre><code class=\"cpp\">typedef enum FMOD_PORT_TYPE {     FMOD_PORT_TYPE_MUSIC,     FMOD_PORT_TYPE_VOICE,     FMOD_PORT_TYPE_FORCEINT = 65536 } FMOD_PORT_TYPE;<\/code><\/pre>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>*<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u0432\u0441\u0442\u0440\u0435\u0447\u0430\u0435\u0442\u0441\u044f \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u043e\u0435 \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0440\u0430\u0437. \u0421\u043f\u0438\u0441\u043e\u043a \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u0435\u0439 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u044b\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u043e\u043c <code>enumerators<\/code>, \u044d\u0442\u043e \u043f\u0440\u0438\u0433\u043e\u0434\u0438\u0442\u0441\u044f \u0434\u0430\u043b\u044c\u0448\u0435 \u043d\u0430 \u044d\u0442\u0430\u043f\u0435 \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u0433\u043e \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u0440\u0430\u0437\u043e\u0431\u0440\u0430\u043d\u043d\u044b\u0445 \u0434\u0430\u043d\u043d\u044b\u0445.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>?<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u043d\u0435\u043e\u0431\u044f\u0437\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u2014 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0442\u0440\u0435\u0447\u0430\u0442\u044c\u0441\u044f \u043d\u043e\u043b\u044c \u0438\u043b\u0438 \u043e\u0434\u0438\u043d \u0440\u0430\u0437.<\/p>\n<pre><code class=\"rust\">Enumerator = { \",\"? ~ name ~ (\"=\" ~ value)? } enumerators = { Enumerator* } Enumeration = {  \"typedef\" ~ \"enum\" ~ name ~ \"{\" ~ enumerators ~ \"}\" ~  name ~ \";\"  }<\/code><\/pre>\n<h3>\u0411\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438<\/h3>\n<p>\u0412 FMOD \u0447\u0430\u0441\u0442\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0442\u0441\u044f \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438, \u0432\u043c\u0435\u0441\u0442\u043e \u0434\u043b\u0438\u043d\u043d\u043e\u0439 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u043b\u043e\u0433\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 \u0432 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438\u043b\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440. \u0424\u043b\u0430\u0433\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <code>typedef<\/code> \u043a\u0430\u043a \u0441\u0438\u043d\u043e\u043d\u0438\u043c \u0431\u0430\u0437\u043e\u0432\u043e\u0433\u043e \u0442\u0438\u043f\u0430, \u044d\u0442\u043e \u0434\u0430\u0435\u0442 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u0443\u044e \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0441\u0442\u044c \u0442\u0438\u043f\u043e\u0432. \u0421 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0434\u0438\u0440\u0435\u043a\u0442\u0438\u0432\u044b <code>#define<\/code> \u0441\u043e\u0437\u0434\u0430\u044e\u0442\u0441\u044f \u043c\u0430\u043a\u0440\u043e\u0441\u044b, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0438\u043c\u0435\u043d\u0443\u044e\u0442 \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u044b\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0444\u043b\u0430\u0433\u043e\u0432:<\/p>\n<pre><code class=\"cpp\">typedef unsigned int FMOD_CHANNELMASK; #define FMOD_CHANNELMASK_FRONT_LEFT     0x00000001 #define FMOD_CHANNELMASK_FRONT_RIGHT    0x00000002 #define FMOD_CHANNELMASK_MONO           (FMOD_CHANNELMASK_FRONT_LEFT) #define FMOD_CHANNELMASK_STEREO         (FMOD_CHANNELMASK_FRONT_LEFT | FMOD_CHANNELMASK_FRONT_RIGHT)<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043f\u043e\u0434\u0445\u043e\u0434\u0438\u0442\u044c \u043a \u0440\u0430\u0437\u0431\u043e\u0440\u0443 \u0442\u0430\u043a\u043e\u0433\u043e \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u043f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 \u044f\u0437\u044b\u043a\u0430 \u0421, \u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438 \u043d\u0435\u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u0442\u0441\u044f \u043d\u0430\u0431\u043e\u0440 \u043d\u0435 \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u044b\u0445 \u043c\u0435\u0436\u0434\u0443 \u0441\u043e\u0431\u043e\u0439 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439. Pest \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u043d\u0430\u043f\u0438\u0441\u0430\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0431\u0443\u0434\u0435\u0442 \u0443\u0441\u0442\u0430\u043d\u0430\u0432\u043b\u0438\u0432\u0430\u0442\u044c \u043a\u043e\u043d\u0442\u0435\u043a\u0441\u0442 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u0431\u0438\u0442\u043e\u0432\u044b\u0445 \u0444\u043b\u0430\u0433\u043e\u0432.<\/p>\n<p>\u041c\u0430\u043a\u0440\u043e\u0441 \u043c\u043e\u0436\u0435\u0442 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u0442\u044c \u043d\u0435 \u0442\u043e\u043b\u044c\u043a\u043e \u043b\u0438\u0442\u0435\u0440\u0430\u043b\u044b, \u043d\u043e \u0438 \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u044b\u0435 \u0432\u044b\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f. \u0427\u0442\u043e\u0431\u044b \u043d\u0435 \u0440\u0430\u0437\u0431\u0438\u0440\u0430\u0442\u044c \u0432\u0441\u0435 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u044b\u0435 \u0441\u0446\u0435\u043d\u0430\u0440\u0438\u0438, \u0432\u044b\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u043e\u043f\u0438\u0441\u044b\u0432\u0430\u044e\u0442\u0441\u044f \u043a\u0430\u043a \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u043b\u044e\u0431\u044b\u0445 \u0441\u0438\u043c\u0432\u043e\u043b\u043e\u0432 <code>ANY<\/code> \u0432 \u0441\u043a\u043e\u0431\u043a\u0430\u0445. \u0423\u043f\u0440\u0435\u0436\u0434\u0430\u044e\u0449\u0438\u0439 \u043e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 <code>!<\/code> \u043e\u0433\u0440\u0430\u043d\u0438\u0447\u0438\u0432\u0430\u0435\u0442 \u0432\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435 \u0437\u0430\u043a\u0440\u044b\u0432\u0430\u044e\u0449\u0435\u0439 \u0441\u043a\u043e\u0431\u043a\u0438.<\/p>\n<pre><code class=\"rust\">Calculation = { \"(\" ~ (!\")\" ~ ANY)* ~ \")\" } Literal = { (\"-\" | \"_\" | ASCII_ALPHANUMERIC)+ } value = @{ Calculation | Literal } Flag = { \"#define\" ~ name ~ value } flags = { Flag+ } flags_type = { FundamentalType } Flags = { \"typedef\" ~ flags_type ~ name ~ \";\" ~ flags  }<\/code><\/pre>\n<h3>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b<\/h3>\n<p>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430 \u2014 \u044d\u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c\u044b\u0439 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0441\u043e\u0441\u0442\u0430\u0432\u043d\u043e\u0439 \u0442\u0438\u043f, \u0438\u043d\u043a\u0430\u043f\u0441\u0443\u043b\u0438\u0440\u0443\u044e\u0449\u0438\u0439\u00a0\u043d\u0430\u0431\u043e\u0440\u00a0\u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u043f\u043e\u043b\u0435\u0439\u00a0\u0440\u0430\u0437\u043b\u0438\u0447\u043d\u044b\u0445 \u0442\u0438\u043f\u043e\u0432. \u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0438\u043c\u0435\u044e\u0442 \u0441\u043b\u043e\u0436\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435. \u0412 \u043d\u0438\u0445 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0442\u0441\u044f \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u0438 \u043c\u0430\u0441\u0441\u0438\u0432\u044b:<\/p>\n<pre><code class=\"cpp\">typedef struct FMOD_DSP_PARAMETER_DESC  {     FMOD_DSP_PARAMETER_TYPE type;     char                    name[16];     char                    label[16];     const char             *description;      union     {         FMOD_DSP_PARAMETER_DESC_FLOAT   floatdesc;         FMOD_DSP_PARAMETER_DESC_INT     intdesc;         FMOD_DSP_PARAMETER_DESC_BOOL    booldesc;         FMOD_DSP_PARAMETER_DESC_DATA    datadesc;     }; } FMOD_DSP_PARAMETER_DESC;<\/code><\/pre>\n<p>\u0422\u0438\u043f\u044b \u043f\u043e\u043b\u0435\u0439:<\/p>\n<ul>\n<li>\n<p>\u0424\u0443\u043d\u0434\u0430\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u0435 \u0442\u0438\u043f\u044b. \u041e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u044b \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043e\u043c \u044f\u0437\u044b\u043a\u0430, \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u044b \u0432 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440. \u041d\u0435\u0442 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u0441\u0442\u0438 \u0440\u0430\u0437\u0431\u0438\u0440\u0430\u0442\u044c \u0432\u0441\u0435 \u0444\u0443\u043d\u0434\u0430\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u0435 \u0442\u0438\u043f\u044b, \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e \u0442\u0435\u0445 \u0447\u0442\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 FMOD<\/p>\n<\/li>\n<li>\n<p>\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0435 \u0442\u0438\u043f\u044b. \u0421\u0438\u043d\u043e\u043d\u0438\u043c\u044b, \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u043d\u044b\u0435 \u043f\u043e\u0434 \u0443\u043d\u0438\u043a\u0430\u043b\u044c\u043d\u044b\u043c\u0438 \u0438\u043c\u0435\u043d\u0430\u043c\u0438 \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 FMOD<\/p>\n<\/li>\n<\/ul>\n<pre><code class=\"rust\">FundamentalType = {     \"char\" | \"unsigned char\" | \"signed char\" |     \"int\" | \"unsigned int\" |     \"short\" | \"unsigned short\" |     \"long long\" | \"long\" | \"unsigned long long\" | \"unsigned long\" |     \"void\" |     \"float\" } UserType = @{ name } field_type = { FundamentalType | UserType }<\/code><\/pre>\n<p>\u041f\u043e\u043b\u044f \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0441\u0438\u043c\u0432\u043e\u043b\u0430 <code>*<\/code>. \u041c\u043e\u0434\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440 \u0442\u0438\u043f\u0430 <code>const<\/code> \u043c\u043e\u0436\u0435\u0442 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c\u0441\u044f \u0434\u043b\u044f \u0437\u0430\u0449\u0438\u0442\u044b \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043f\u043e\u043b\u044f \u043e\u0442 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0433\u043e \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u0438\u044f \u043f\u043e \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044e.<\/p>\n<pre><code class=\"rust\">as_const = { \"const\" } NormalPointer = { \"*\" } DoublePointer = { \"**\" } pointer = { DoublePointer | NormalPointer }<\/code><\/pre>\n<p>\u041e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u0442 \u043d\u0430\u0431\u043e\u0440 \u043f\u043e\u043b\u0435\u0439 \u0438 \u0445\u0440\u0430\u043d\u0438\u0442 \u0442\u043e\u043b\u044c\u043a\u043e \u043e\u0434\u043d\u043e \u0438\u0437 \u043d\u0438\u0445. \u041f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 C, \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u043c\u043e\u0436\u043d\u043e \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u0442\u044c \u0442\u0435\u0433\u043e\u043c, \u043d\u043e \u0432 FMOD \u044d\u0442\u043e \u043d\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f. \u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u043f\u043e\u0434\u0447\u0438\u043d\u044f\u044e\u0442\u0441\u044f \u0442\u0435\u043c \u0436\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430\u043c, \u0447\u0442\u043e \u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b:<\/p>\n<pre><code class=\"rust\">union = { \"union\" ~ \"{\" ~ fields ~ \"}\" ~ \";\" }<\/code><\/pre>\n<p>\u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u043c\u0430\u0441\u0441\u0438\u0432\u0430 \u044d\u0442\u043e \u0447\u0430\u0441\u0442\u044c \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u0438\u044f \u043f\u043e\u043b\u044f, \u0430 \u043d\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0442\u0438\u043f\u0430. \u0427\u0438\u0441\u043b\u043e \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u043e\u0432 \u043c\u0430\u0441\u0441\u0438\u0432\u0430 \u043c\u043e\u0436\u0435\u0442 \u0431\u044b\u0442\u044c \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043e \u0447\u0435\u0440\u0435\u0437 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u0443:<\/p>\n<pre><code class=\"rust\">as_array = { \"[\" ~ (\"_\" | ASCII_ALPHANUMERIC)+ ~ \"]\" }<\/code><\/pre>\n<p>\u0411\u043b\u0430\u0433\u043e\u0434\u0430\u0440\u044f \u0432\u044b\u0440\u0430\u0437\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a \u043f\u043e\u043b\u043d\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u0443\u043c\u0435\u0449\u0430\u0435\u0442\u0441\u044f \u0431\u0443\u043a\u0432\u0430\u043b\u044c\u043d\u043e \u0432 \u043f\u0430\u0440\u0443 \u0434\u0435\u0441\u044f\u0442\u043a\u043e\u0432 \u0441\u0442\u0440\u043e\u043a:<\/p>\n<pre><code class=\"rust\">as_const = { \"const\" } as_array = { \"[\" ~ (\"_\" | ASCII_ALPHANUMERIC)+ ~ \"]\" } NormalPointer = { \"*\" } DoublePointer = { \"**\" } pointer = { DoublePointer | NormalPointer }  field_type = { FundamentalType | UserType } Field = { as_const? ~ field_type ~ pointer? ~ name ~ as_array? ~ \";\" } fields = { Field* }  union = { \"union\" ~ \"{\" ~ fields ~ \"}\" ~ \";\" }  Structure = {  \"typedef\"? ~ \"struct\" ~ name ~ \"{\" ~  fields ~  union? ~  \"}\" ~ name? ~ \";\"  }<\/code><\/pre>\n<h2>\u0424\u0443\u043d\u043a\u0446\u0438\u0438<\/h2>\n<p>\u0424\u0443\u043d\u043a\u0446\u0438\u044f \u2014 \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0439 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u043d\u044b\u0439 \u044d\u043b\u0435\u043c\u0435\u043d\u0442, \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043e\u0442\u043e\u0440\u043e\u0433\u043e \u0440\u0435\u0448\u0430\u044e\u0442\u0441\u044f \u0437\u0430\u0434\u0430\u0447\u0438 FMOD. \u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u043e \u043e\u0442 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442\u0441\u044f \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432, \u0432\u043a\u043b\u044e\u0447\u0430\u0435\u0442 \u0432 \u0441\u0435\u0431\u044f \u0438\u043c\u044f, \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0439 \u0442\u0438\u043f \u0438 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b \u0444\u0443\u043d\u043a\u0446\u0438\u0438.<\/p>\n<pre><code class=\"cpp\">FMOD_RESULT F_API FMOD_System_Create (FMOD_SYSTEM **system, unsigned int headerversion);<\/code><\/pre>\n<p>\u0422\u043e\u043b\u044c\u043a\u043e \u0443 \u0433\u043b\u043e\u0431\u0430\u043b\u044c\u043d\u044b\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 FMOD \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u044b\u0439 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0439 \u0442\u0438\u043f. \u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u044a\u0435\u043a\u0442\u043e\u0432 \u0432\u0441\u0435\u0433\u0434\u0430 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442 \u0441\u0442\u0430\u0442\u0443\u0441 \u0432\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u044f <code>FMOD_RESULT<\/code>, \u0430 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0447\u0435\u0440\u0435\u0437 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u0432 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430\u0445.<\/p>\n<p>\u0410\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u044e\u0442 \u043d\u0430\u0431\u043e\u0440 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0431\u0443\u0434\u0443\u0442 \u043f\u0435\u0440\u0435\u0434\u0430\u0432\u0430\u0442\u044c\u0441\u044f \u0432 \u0444\u0443\u043d\u043a\u0446\u0438\u044e \u043f\u0440\u0438 \u0432\u044b\u0437\u043e\u0432\u0435. \u0422\u0438\u043f \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430 \u043c\u043e\u0436\u0435\u0442 \u0431\u044b\u0442\u044c \u043b\u044e\u0431\u044b\u043c, \u0444\u0443\u043d\u0434\u0430\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u043c \u0438\u043b\u0438 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u043c.<\/p>\n<p>\u0410\u0442\u0440\u0438\u0431\u0443\u0442\u044b \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0441\u043a\u0440\u044b\u0442\u044b\u0435 \u0437\u0430 \u043c\u0430\u043a\u0440\u043e\u0441\u043e\u043c <code>F_API<\/code> \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u044e\u0442 \u0441\u043f\u0435\u0446\u0438\u0444\u0438\u0447\u043d\u044b\u0435 \u0434\u043b\u044f \u043f\u043b\u0430\u0442\u0444\u043e\u0440\u043c\u044b \u0441\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u044f \u043e \u0432\u044b\u0437\u043e\u0432\u0430\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0438, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 <code>__stdcall<\/code>.<\/p>\n<pre><code class=\"rust\">argument_type = { FundamentalType | UserType } Argument = { as_const? ~ argument_type ~ pointer? ~ name } arguments = { (\",\"? ~ Argument)* } return_type = { FundamentalType | UserType } Function = { return_type ~ \"F_API\" ~ name ~  \"(\" ~ arguments ~ \")\" \";\" }<\/code><\/pre>\n<h3>\u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430<\/h3>\n<p>\u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430 \u043f\u0435\u0440\u0435\u0434\u0430\u044e\u0442\u0441\u044f \u0447\u0435\u0440\u0435\u0437 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c. \u041d\u043e \u0444\u0443\u043d\u043a\u0446\u0438\u0438, \u0432 \u043e\u0442\u043b\u0438\u0447\u0438\u0435 \u043e\u0442 \u0434\u0440\u0443\u0433\u0438\u0445 \u043f\u0440\u0438\u043c\u0438\u0442\u0438\u0432\u043e\u0432 \u0438\u043c\u0435\u044e\u0442 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u0438 \u0441\u043f\u0438\u0441\u043e\u043a \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432, \u044d\u0442\u043e \u043f\u0440\u0438\u0432\u043e\u0434\u0438\u0442 \u043a \u0434\u043b\u0438\u043d\u043d\u043e\u043c\u0443 \u0438 \u0441\u043b\u043e\u0436\u043d\u043e\u043c\u0443 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044e \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f. \u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0447\u0435\u0440\u0435\u0437 <code>typedef<\/code> \u0443\u043f\u0440\u043e\u0449\u0430\u0435\u0442 \u0440\u0430\u0431\u043e\u0442\u0443 \u0441 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f\u043c\u0438 \u043d\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u044e.<\/p>\n<p>\u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 FMOD \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u044b \u0441 \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u044b\u043c \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e\u043c \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432. \u0421\u043f\u0438\u0441\u043e\u043a \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432 \u0434\u043e\u043b\u0436\u0435\u043d \u0437\u0430\u043a\u0430\u043d\u0447\u0438\u0432\u0430\u0442\u044c\u0441\u044f \u0437\u0430\u043f\u044f\u0442\u043e\u0439 \u0438 \u0442\u0440\u0435\u043c\u044f \u0442\u043e\u0447\u043a\u0430\u043c\u0438, \u0447\u0442\u043e\u0431\u044b \u0443\u043a\u0430\u0437\u0430\u0442\u044c, \u0447\u0442\u043e \u0432 \u0444\u0443\u043d\u043a\u0446\u0438\u044e \u043c\u043e\u0433\u0443\u0442 \u0431\u044b\u0442\u044c \u043f\u0435\u0440\u0435\u0434\u0430\u043d\u044b \u0434\u043e\u043f\u043e\u043b\u043d\u0438\u0442\u0435\u043b\u044c\u043d\u044b\u0435 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b.<\/p>\n<pre><code class=\"cpp\">typedef void (F_CALL *FMOD_DSP_LOG_FUNC)  (FMOD_DEBUG_FLAGS level, const char *file, const char *string, ...);<\/code><\/pre>\n<p>\u0411\u043e\u043b\u044c\u0448\u0438\u043d\u0441\u0442\u0432\u043e \u043f\u0440\u0430\u0432\u0438\u043b \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u043e\u0432\u0442\u043e\u0440\u043d\u043e, \u043f\u0440\u0438 \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e\u043c \u0443\u0440\u043e\u0432\u043d\u0435 \u0433\u0440\u0430\u043d\u0443\u043b\u044f\u0440\u043d\u043e\u0441\u0442\u0438 \u044d\u0442\u0438\u0445 \u043f\u0440\u0430\u0432\u0438\u043b:<\/p>\n<pre><code class=\"rust\">varargs = { \",\" ~ \"...\" } Callback = {  \"typedef\" ~ return_type ~ pointer? ~ (\"F_CALL\" ~ \"*\" ~ name ~ \")\" ~  \"(\" ~ arguments ~ varargs?  ~ \")\" ~  \";\"  }<\/code><\/pre>\n<h3>\u041f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435 API<\/h3>\n<p>\u0427\u0442\u043e\u0431\u044b \u0438\u0437\u0432\u043b\u0435\u0447\u044c \u0434\u0430\u043d\u043d\u044b\u0435, \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0435 \u0434\u043b\u044f \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0438, \u043d\u0443\u0436\u043d\u043e \u0432\u0440\u0443\u0447\u043d\u0443\u044e \u043f\u0440\u043e\u0439\u0442\u0438 \u043f\u043e \u0434\u0435\u0440\u0435\u0432\u0443 \u0440\u0430\u0437\u0431\u043e\u0440\u0430:<\/p>\n<pre><code class=\"rust\">for declaration in declarations.into_inner() {     match declaration.as_rule() {         Rule::Function => {             let mut inner_rules = line.into_inner();             let name = inner_rules.next().unwrap().as_str();             let return_type_rule = inner_rules.next().unwrap().as_rule();             let return_type = match return_type_rule {                 Rule::FundamentalType => return_type_rule.as_str(),                 Rule::UserType => return_type_rule.as_str(),                 _ => unreachable!()             }             \/\/ ...         },         _ => continue,     } }<\/code><\/pre>\n<p>\u042d\u0442\u043e \u043e\u0442\u043a\u0440\u043e\u0432\u0435\u043d\u043d\u043e \u0441\u043b\u0430\u0431\u043e\u0435 \u043c\u0435\u0441\u0442\u043e pest. \u0414\u0435\u043b\u0430\u0435\u0442 \u0440\u0435\u0448\u0435\u043d\u0438\u0435 \u043f\u043e\u0434\u0432\u0435\u0440\u0436\u0435\u043d\u043d\u044b\u043c \u043e\u0448\u0438\u0431\u043a\u0430\u043c, \u0442\u0440\u0443\u0434\u043d\u044b\u043c \u0434\u043b\u044f \u0447\u0442\u0435\u043d\u0438\u044f \u0438 \u0441\u043b\u043e\u0436\u043d\u044b\u043c \u0432 \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0438 \u043f\u0440\u0430\u0432\u0438\u043b \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438. \u0414\u0430\u0436\u0435 \u043f\u043e\u0434\u0441\u0432\u0435\u0442\u043a\u0430 \u043a\u043e\u0434\u0430 \u0432 IDE \u043d\u0430 \u044d\u0442\u043e\u043c \u0443\u0447\u0430\u0441\u0442\u043a\u0435 \u043d\u0435 \u0440\u0430\u0431\u043e\u0442\u0430\u0435\u0442. \u0422\u0430\u043a \u043f\u0440\u043e\u0438\u0441\u0445\u043e\u0434\u0438\u0442 \u043f\u043e\u0442\u043e\u043c\u0443, \u0447\u0442\u043e \u043f\u0430\u0440\u0441\u0435\u0440 \u0438 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u044e\u0442\u0441\u044f \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u0438 <code>pest_derive<\/code> \u0442\u043e\u043b\u044c\u043a\u043e \u0432 \u043c\u043e\u043c\u0435\u043d\u0442 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0446\u0438\u0438 Rust \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u044f.<\/p>\n<p>\u0421\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0442 \u0440\u0435\u0448\u0435\u043d\u0438\u044f, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043f\u044b\u0442\u0430\u044e\u0442\u0441\u044f \u0438\u0441\u043f\u0440\u0430\u0432\u0438\u0442\u044c \u044d\u0442\u0443 \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0443, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 <code>pest_consume<\/code>. \u041e\u043d \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0442\u0438\u043f\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0439 \u043e\u0431\u0445\u043e\u0434 \u0434\u0435\u0440\u0435\u0432\u0430.<\/p>\n<p>\u0421\u0438\u0442\u0443\u0430\u0446\u0438\u044e \u043c\u043e\u0436\u043d\u043e \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u0435\u0449\u0435 \u043b\u0443\u0447\u0448\u0435, \u0435\u0441\u043b\u0438 \u0434\u0435\u0440\u0435\u0432\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u043d\u0430\u0447\u0430\u043b\u0430 \u0432 \u043e\u0431\u0449\u0435\u043c \u0432\u0438\u0434\u0435 \u043f\u0440\u0438\u0432\u0435\u0441\u0442\u0438 \u043a \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u043c\u0443 \u0444\u043e\u0440\u043c\u0430\u0442\u0443. \u0410 \u0437\u0430\u0442\u0435\u043c \u0438\u0437 \u044d\u0442\u043e\u0433\u043e \u0444\u043e\u0440\u043c\u0430\u0442\u0430 \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u044c \u0434\u0430\u043d\u043d\u044b\u0435 \u0432 \u0442\u0438\u043f\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430\u0445. \u041d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c <code>serde_json<\/code> \u0438 \u0442\u0440\u0430\u043d\u0441\u043b\u044f\u0446\u0438\u044e \u0432 JSON.<\/p>\n<p>\u0414\u0435\u0440\u0435\u0432\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430 pest \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0438\u0437 \u0441\u0435\u0431\u044f \u0441\u043f\u0438\u0441\u043e\u043a \u0441\u043f\u0438\u0441\u043a\u043e\u0432. \u0427\u0442\u043e\u0431\u044b \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0433\u0434\u0435 \u0437\u0430\u043a\u0430\u043d\u0447\u0438\u0432\u0430\u0435\u0442\u0441\u044f \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u043e\u0432 \u043e\u0434\u043d\u043e\u0433\u043e \u043e\u0431\u044a\u0435\u043a\u0442\u0430 \u0438 \u043d\u0430\u0447\u0438\u043d\u0430\u0435\u0442\u0441\u044f \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0435 \u0432\u043b\u043e\u0436\u0435\u043d\u043d\u044b\u0445 \u043e\u0431\u044a\u0435\u043a\u0442\u043e\u0432, \u044f\u0432\u043d\u043e \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u043c \u0441\u043f\u0438\u0441\u043e\u043a \u043f\u0440\u0430\u0432\u0438\u043b, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442 \u044d\u0442\u0438 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f.<\/p>\n<details class=\"spoiler\">\n<summary>\u041a\u043e\u0434 JSON \u043a\u043e\u043d\u0432\u0435\u0440\u0442\u0435\u0440\u0430<\/summary>\n<div class=\"spoiler__content\">\n<pre><code class=\"rust\">pub struct JsonConverter {     pub arrays: Vec&lt;String>, }  impl JsonConverter {     pub fn new(arrays: Vec&lt;String>) -> Self {         JsonConverter { arrays }     }      pub fn convert&lt;T, R>(&amp;self, pair: Pair&lt;'_, R>) -> Result&lt;T, serde_json::Error>     where         T: DeserializeOwned,         R: RuleType,     {         let value = self.create_value(pair);         serde_json::from_value(value)     }          pub fn create_value&lt;R>(&amp;self, pair: Pair&lt;'_, R>) -> Value     where         R: RuleType,     {         let rule = format!(\"{:?}\", pair.as_rule());         let data = pair.as_str();         let inner = pair.into_inner();         if inner.peek().is_none() {             Value::String(data.into())         } else {             if self.arrays.contains(&amp;rule) {                 let values = inner.map(|pair| self.create_value(pair)).collect();                 Value::Array(values)             } else {                 let map = inner.map(|pair| {                     let key = format!(\"{:?}\", pair.as_rule());                     let value = self.create_value(pair);                     (key, value)                 });                 Value::Object(Map::from_iter(map))             }         }     } }<\/code><\/pre>\n<\/div>\n<\/details>\n<p>\u0412 \u0438\u0442\u043e\u0433\u0435 \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0442\u0438\u043f\u0438\u0437\u0438\u0440\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442 \u0432\u0441\u0435 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435 \u0434\u043b\u044f \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0438:<\/p>\n<pre><code class=\"rust\">#[derive(Debug, Clone, Serialize, Deserialize, PartialEq)] pub enum Type {     FundamentalType(String),     UserType(String), }  #[derive(Debug, Clone, Serialize, Deserialize, PartialEq)] pub struct Argument {     pub as_const: Option&lt;String>,     pub argument_type: Type,     pub pointer: Option&lt;Pointer>,     pub name: String, }  #[derive(Debug, Clone, Serialize, Deserialize, PartialEq)] pub struct Function {     pub return_type: Type,     pub name: String,     pub arguments: Vec&lt;Argument>, }<\/code><\/pre>\n<h2>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f FFI<\/h2>\n<p>\u0411\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0430 quote \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c \u043a\u0432\u0430\u0437\u0438-\u0446\u0438\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f. \u0418\u0434\u0435\u044f \u0432 \u0442\u043e\u043c, \u0447\u0442\u043e \u0432 \u043c\u0430\u043a\u0440\u043e\u0441\u0435 <code>quote!<\/code> \u043f\u0438\u0448\u0435\u043c \u0447\u0442\u043e-\u0442\u043e \u043e\u0447\u0435\u043d\u044c \u043f\u043e\u0445\u043e\u0436\u0435\u0435 \u043d\u0430 \u0438\u0442\u043e\u0433\u043e\u0432\u044b\u0439 Rust \u043a\u043e\u0434. \u041f\u0440\u0438 \u044d\u0442\u043e\u043c \u0440\u0430\u0431\u043e\u0442\u0430\u044e\u0442 \u0432\u0441\u0435 \u0443\u0434\u043e\u0431\u0441\u0442\u0432\u0430 \u0440\u0435\u0434\u0430\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u0432 IDE: \u043f\u043e\u0434\u0441\u0432\u0435\u0442\u043a\u0430 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441\u0430, \u0430\u0432\u0442\u043e-\u0434\u043e\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u0435, \u043e\u0442\u0441\u0442\u0443\u043f\u044b. \u0418 \u0432 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442\u0435 \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u043f\u043e\u0442\u043e\u043a \u0442\u043e\u043a\u0435\u043d\u043e\u0432 \u0438\u0441\u0445\u043e\u0434\u043d\u043e\u0433\u043e \u043a\u043e\u0434\u0430, \u0441 \u043a\u043e\u0442\u043e\u0440\u044b\u043c \u043c\u043e\u0436\u043d\u043e \u043e\u0431\u0440\u0430\u0449\u0430\u0442\u044c\u0441\u044f \u043a\u0430\u043a \u0441 \u0434\u0430\u043d\u043d\u044b\u043c\u0438.<\/p>\n<pre><code class=\"rust\">#[proc_macro] pub fn make_pub(item: TokenStream) -> TokenStream {     quote! {       pub #item     } }  make_pub! {     const X: u32 = 42; }<\/code><\/pre>\n<p>\u0418\u0437\u043d\u0430\u0447\u0430\u043b\u044c\u043d\u043e \u044d\u0442\u043e\u0442 \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c \u0441\u043e\u0437\u0434\u0430\u043d \u0434\u043b\u044f \u043d\u0430\u043f\u0438\u0441\u0430\u043d\u0438\u044f \u043f\u0440\u043e\u0446\u0435\u0434\u0443\u0440\u043d\u044b\u0445 \u043c\u0430\u043a\u0440\u043e\u0441\u043e\u0432, \u043d\u043e \u043f\u043e \u0441\u0443\u0442\u0438 \u044d\u0442\u043e \u0443\u043d\u0438\u0432\u0435\u0440\u0441\u0430\u043b\u044c\u043d\u043e\u0435 \u0440\u0435\u0448\u0435\u043d\u0438\u0435. \u0415\u0433\u043e \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0432\u043c\u0435\u0441\u0442\u043e \u043e\u0431\u044b\u0447\u043d\u043e\u0433\u043e \u0448\u0430\u0431\u043b\u043e\u043d\u0438\u0437\u0430\u0442\u043e\u0440\u0430 \u0434\u043b\u044f \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0438 Rust \u043a\u043e\u0434\u0430, \u043f\u043e\u043b\u0443\u0447\u0438\u0432 \u043f\u0440\u0438 \u044d\u0442\u043e\u043c \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u043e \u043f\u0440\u0435\u0438\u043c\u0443\u0449\u0435\u0441\u0442\u0432:<\/p>\n<ul>\n<li>\n<p>\u041c\u0435\u043d\u044c\u0448\u0435 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u043e\u0448\u0438\u0431\u043e\u043a, \u0431\u044b\u0441\u0442\u0440\u0435\u0435 \u0440\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0430<\/p>\n<\/li>\n<li>\n<p>\u041d\u0435 \u043d\u0443\u0436\u043d\u043e \u0434\u0443\u043c\u0430\u0442\u044c \u043d\u0430\u0434 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435\u043c \u0434\u0430\u043d\u043d\u044b\u0445 \u0434\u043b\u044f \u0448\u0430\u0431\u043b\u043e\u043d\u0438\u0437\u0430\u0442\u043e\u0440\u0430<\/p>\n<\/li>\n<li>\n<p>\u041c\u043e\u0434\u0443\u043b\u044c\u043d\u043e\u0441\u0442\u044c, \u0442\u043e\u043a\u0435\u043d\u044b \u043f\u0440\u043e\u0438\u0437\u0432\u0435\u0434\u0435\u043d\u043d\u044b\u0435 <code>quote!<\/code> \u043c\u043e\u0433\u0443\u0442 \u0431\u044b\u0442\u044c \u0432\u043b\u043e\u0436\u0435\u043d\u044b \u0432 \u0434\u0440\u0443\u0433\u043e\u0439 <code>quote!<\/code><\/p>\n<\/li>\n<\/ul>\n<pre><code class=\"rust\">pub fn generate_ffi_code(api: &amp;Api) -> Result&lt;TokenStream, Error> {     let opaque_types = api.opaque_types.iter().map(generate_opaque_type);     \/\/ let type_aliases = ...      Ok(quote! {         #![allow(non_camel_case_types)]         #![allow(non_snake_case)]         #![allow(unused_parens)]         use std::mem::size_of;         use std::ptr::null_mut;          #(#opaque_types)*         #(#type_aliases)*         #(#constants)*         #(#enumerations)*         #(#flags)*         #(#structures)*         #(#presets)*         #(#callbacks)*         #(#libraries)*         #errors     }) }<\/code><\/pre>\n<h3>\u041d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u044b\u0435 \u0442\u0438\u043f\u044b<\/h3>\n<p>\u0412\u043a\u043b\u044e\u0447\u0430\u044f \u0445\u043e\u0442\u044f \u0431\u044b \u043e\u0434\u043d\u043e \u043f\u0440\u0438\u0432\u0430\u0442\u043d\u043e\u0435 \u043f\u043e\u043b\u0435 \u0438 \u043d\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044f \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0442\u043e\u0440, \u043c\u043e\u0436\u043d\u043e \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u0442\u044c \u043d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u0443\u044e \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443 \u0432 Rust, \u044d\u043a\u0437\u0435\u043c\u043f\u043b\u044f\u0440 \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u043d\u0435\u043b\u044c\u0437\u044f \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0432\u043d\u0435 FMOD. \u041f\u0440\u0438\u0432\u0430\u0442\u043d\u043e\u0435 \u043f\u043e\u043b\u0435 <code>_unused<\/code> \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e, \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430 \u0431\u0435\u0437 \u043f\u043e\u043b\u044f \u043c\u043e\u0436\u0435\u0442 \u0431\u044b\u0442\u044c \u0441\u043e\u0437\u0434\u0430\u043d\u0430 \u043a\u0435\u043c \u0443\u0433\u043e\u0434\u043d\u043e. \u0414\u043b\u044f \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u044d\u0442\u043e\u0433\u043e \u0442\u0438\u043f\u0430 \u0432 FFI \u043d\u0443\u0436\u043d\u043e \u0434\u043e\u0431\u0430\u0432\u0438\u0442\u044c \u043c\u0430\u0440\u043a\u0435\u0440 <code>#[repr(C)]<\/code>.<\/p>\n<p>\u0418\u043d\u0442\u0435\u0440\u043f\u043e\u043b\u044f\u0446\u0438\u044f \u0434\u0430\u043d\u043d\u044b\u0445 \u0432 <code>quote!<\/code> \u0432\u044b\u043f\u043e\u043b\u043d\u044f\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <code>#name<\/code>. \u042d\u0442\u043e \u0437\u0430\u0445\u0432\u0430\u0442\u044b\u0432\u0430\u0435\u0442 \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u0443\u044e <code>name<\/code>, \u0438 \u0432\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0435\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u0435 \u043c\u0435\u0441\u0442\u043e \u0432 \u043f\u043e\u0442\u043e\u043a\u0435 \u0442\u043e\u043a\u0435\u043d\u043e\u0432.<\/p>\n<p>\u0418\u043d\u0442\u0435\u0440\u043f\u043e\u043b\u044f\u0446\u0438\u044f \u0440\u0430\u0431\u043e\u0442\u0430\u0435\u0442 \u0434\u043b\u044f \u0432\u0441\u0435\u0445 \u0431\u0430\u0437\u043e\u0432\u044b\u0445 \u0442\u0438\u043f\u043e\u0432 Rust. \u0414\u043b\u044f \u0441\u0442\u0440\u043e\u043a\u0438 \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u0432\u044b\u0433\u043b\u044f\u0434\u0435\u0442\u044c \u043a\u0430\u043a \u0432\u0441\u0442\u0430\u0432\u043a\u0430 \u0441\u0442\u0440\u043e\u043a\u043e\u0432\u043e\u0433\u043e \u043b\u0438\u0442\u0435\u0440\u0430\u043b\u0430 \u0432 \u043a\u0430\u0432\u044b\u0447\u043a\u0430\u0445. \u0427\u0442\u043e\u0431\u044b \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0442\u043e\u043a\u0435\u043d \u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440\u0430, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 \u0434\u043b\u044f \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u0438\u044f \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b, \u043d\u0443\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043c\u0430\u043a\u0440\u043e\u0441 <code>format_ident!<\/code>.<\/p>\n<pre><code class=\"rust\">pub fn generate_opaque_type(value: &amp;OpaqueType) -> TokenStream {     let name = format_ident!(\"{}\", value.name);     quote! {         #[repr(C)]         #[derive(Debug, Copy, Clone)]         pub struct #name {             _unused: [u8; 0]         }     } }<\/code><\/pre>\n<p>\u041f\u043e\u0441\u043a\u043e\u043b\u044c\u043a\u0443 \u0434\u043b\u044f \u043a\u0430\u0436\u0434\u043e\u0433\u043e FMOD \u043e\u0431\u044a\u0435\u043a\u0442\u0430 \u043c\u044b \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c \u0440\u0430\u0437\u043d\u044b\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b, \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u043c \u0442\u0438\u043f\u043e\u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0442\u044c \u2014 \u043d\u0435 \u0441\u043c\u043e\u0436\u0435\u043c, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u0441\u043b\u0443\u0447\u0430\u0439\u043d\u043e \u043e\u0442\u043f\u0440\u0430\u0432\u0438\u0442\u044c \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0430 <code>FMOD_SYSTEM<\/code> \u0442\u0443\u0434\u0430, \u0433\u0434\u0435 \u043e\u0436\u0438\u0434\u0430\u0435\u0442\u0441\u044f \u043e\u0431\u044a\u0435\u043a\u0442 <code>FMOD_SOUND<\/code>.<\/p>\n<pre><code class=\"rust\">#[repr(C)] #[derive(Debug, Copy, Clone)] pub struct FMOD_SYSTEM {   _unused: [u8; 0], }  #[repr(C)] #[derive(Debug, Copy, Clone)] pub struct FMOD_SOUND {   _unused: [u8; 0], }<\/code><\/pre>\n<h3>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f<\/h3>\n<p>\u0412 Rust \u043d\u0435\u0442 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f \u0434\u043b\u044f \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u044b\u0445 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0439. \u0414\u043b\u044f \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0442\u0438\u043f\u0430 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u043f\u0441\u0435\u0432\u0434\u043e\u043d\u0438\u043c \u043d\u0430 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u0439 \u0431\u0430\u0437\u043e\u0432\u044b\u0439 \u0442\u0438\u043f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0433\u043e \u0441\u043b\u043e\u0432\u0430 <code>type<\/code>. \u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u044f\u0435\u043c \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u0430\u043c\u0438.<\/p>\n<p>\u041a\u0430\u0436\u0434\u043e\u043c\u0443 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044e \u043f\u0440\u0438\u0441\u0432\u0430\u0438\u0432\u0430\u0435\u0442\u0441\u044f \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435, \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u044e\u0449\u0435\u0435 \u0435\u0433\u043e \u043c\u0435\u0441\u0442\u0443 \u0432 \u043f\u043e\u0440\u044f\u0434\u043a\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439. \u041f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e \u043f\u0435\u0440\u0432\u043e\u043c\u0443 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044e \u043f\u0440\u0438\u0441\u0432\u0430\u0438\u0432\u0430\u0435\u0442\u0441\u044f 0, \u0441\u043b\u0435\u0434\u0443\u044e\u0449\u0435\u043c\u0443 \u043f\u0440\u0438\u0441\u0432\u0430\u0438\u0432\u0430\u0435\u0442\u0441\u044f 1 \u0438 \u0434\u0430\u043b\u0435\u0435. \u0422\u0430\u043a \u0436\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043c\u043e\u0433\u0443\u0442 \u0431\u044b\u0442\u044c \u0443\u043a\u0430\u0437\u0430\u043d\u044b \u044f\u0432\u043d\u043e.<\/p>\n<p>\u041f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u0435 \u0432 <code>quote!<\/code> \u0432\u044b\u043f\u043e\u043b\u043d\u044f\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <code>#(#enumerators)*<\/code>. \u042d\u0442\u043e \u043f\u0435\u0440\u0435\u0431\u0438\u0440\u0430\u0435\u0442 \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u044b \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u043e\u0439 <code>enumerators<\/code>, \u0438 \u0432\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442 \u0438\u043d\u0442\u0435\u0440\u043f\u043e\u043b\u044f\u0446\u0438\u0438 \u043a\u0430\u0436\u0434\u043e\u0433\u043e \u0438\u0437 \u043d\u0438\u0445 \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u0435 \u043c\u0435\u0441\u0442\u043e.<\/p>\n<pre><code class=\"rust\">pub fn generate_enumeration( enumeration: &amp;Enumeration ) -> Result&lt;TokenStream, Error> {     let name = format_ident!(\"{}\", enumeration.name);     let mut value: i32 = -1;     let mut enumerators = vec![];     for enumerator in &amp;enumeration.enumerators {         let label = format_ident!(\"{}\", &amp;enumerator.name);         let value = match &amp;enumerator.value {             None => {                 value += 1;                 value             }             Some(repr) => {                 value = repr.parse()?;                 value             }         };         let literal = Literal::i32_unsuffixed(value);         enumerators.push(quote! {             pub const #label: #name = #literal;         });     }     Ok(quote! {         pub type #name = c_int;         #(#enumerators)*     }) }<\/code><\/pre>\n<p>\u041f\u0441\u0435\u0432\u0434\u043e\u043d\u0438\u043c\u044b \u043d\u0435 \u0433\u0430\u0440\u0430\u043d\u0442\u0438\u0440\u0443\u044e\u0442 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0441\u0442\u044c \u0438\u0445 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f. \u0412\u043c\u0435\u0441\u0442\u043e \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u043e\u0433\u043e \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u043c\u043e\u0436\u043d\u043e \u043f\u0435\u0440\u0435\u0434\u0430\u0442\u044c \u043b\u044e\u0431\u043e\u0435 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u043f\u043e \u043e\u0448\u0438\u0431\u043a\u0435. \u0412 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u0435 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u0438\u0441\u043f\u0440\u0430\u0432\u043b\u0435\u043d\u043e, \u0430 \u043d\u0430 \u0443\u0440\u043e\u0432\u043d\u0435 FFI \u044d\u0442\u043e \u0443\u0432\u0435\u043b\u0438\u0447\u0438\u0432\u0430\u0435\u0442 \u0447\u0438\u0442\u0430\u0435\u043c\u043e\u0441\u0442\u044c \u0441\u0438\u0433\u043d\u0430\u0442\u0443\u0440 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440:<\/p>\n<pre><code class=\"rust\">pub type FMOD_PLUGINTYPE = c_int; pub const FMOD_PLUGINTYPE_OUTPUT: FMOD_PLUGINTYPE = 0; pub const FMOD_PLUGINTYPE_CODEC: FMOD_PLUGINTYPE = 1; pub const FMOD_PLUGINTYPE_DSP: FMOD_PLUGINTYPE = 2; pub const FMOD_PLUGINTYPE_MAX: FMOD_PLUGINTYPE = 3; pub const FMOD_PLUGINTYPE_FORCEINT: FMOD_PLUGINTYPE = 65536;<\/code><\/pre>\n<h3>\u0411\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438<\/h3>\n<p>\u0411\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438 \u2014 \u044d\u0442\u043e \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435 \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u0438\u0445 \u043b\u043e\u0433\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 \u0438\u043b\u0438 \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u0438\u0445 \u0441\u043e\u0441\u0442\u043e\u044f\u043d\u0438\u0439 \u043e\u0434\u043d\u0438\u043c \u0446\u0435\u043b\u044b\u043c \u0447\u0438\u0441\u043b\u043e\u043c. \u041a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043c\u043e\u0436\u043d\u043e \u0445\u0440\u0430\u043d\u0438\u0442\u044c \u0432\u043d\u0443\u0442\u0440\u0438 \u043e\u0434\u043d\u043e\u0433\u043e \u0447\u0438\u0441\u043b\u0430 \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043e\u0442 \u0440\u0430\u0437\u0440\u044f\u0434\u043d\u043e\u0441\u0442\u0438. \u041d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, 32-\u0440\u0430\u0437\u0440\u044f\u0434\u043d\u043e\u0435 \u0447\u0438\u0441\u043b\u043e \u043c\u043e\u0436\u0435\u0442 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442\u044c 32 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043f\u043e \u043e\u0434\u043d\u043e\u043c\u0443 \u0431\u0438\u0442\u0443 \u043d\u0430 \u043a\u0430\u0436\u0434\u043e\u0435 \u0441\u043e\u0441\u0442\u043e\u044f\u043d\u0438\u0435. <\/p>\n<p>\u0412 FMOD \u0432\u0441\u0442\u0440\u0435\u0447\u0430\u0435\u0442\u0441\u044f \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u043e \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u043e\u0432 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 \u044d\u0442\u0438\u0445 \u0444\u043b\u0430\u0433\u043e\u0432:<\/p>\n<ul>\n<li>\n<p>\u041b\u0438\u0442\u0435\u0440\u0430\u043b\u044b \u0432 \u0448\u0435\u0441\u0442\u043d\u0430\u0434\u0446\u0430\u0442\u0435\u0440\u0438\u0447\u043d\u043e\u0439 \u0444\u043e\u0440\u043c\u0435 <code>0x00000400<\/code><\/p>\n<\/li>\n<li>\n<p>\u0421\u0434\u0432\u0438\u0433\u0438 <code>(1 &lt;&lt; 4)<\/code><\/p>\n<\/li>\n<li>\n<p>\u0411\u0438\u0442\u043e\u0432\u044b\u0435 \u043e\u043f\u0435\u0440\u0430\u0446\u0438\u0438 <code>(CHANNELMASK_FRONT_LEFT | CHANNELMASK_FRONT_RIGHT)<\/code><\/p>\n<\/li>\n<\/ul>\n<p>\u0412\u0441\u0435 \u044d\u0442\u0438 \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u044b \u2014 \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u043d\u044b\u0435 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u0438\u0435 \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0446\u0438\u0438 \u0438 \u0432 Rust, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u043e\u043b\u043d\u044b\u0439 \u0440\u0430\u0437\u0431\u043e\u0440 \u0438 \u0438\u043d\u0442\u0435\u0440\u043f\u0440\u0435\u0442\u0430\u0446\u0438\u044e \u0434\u0435\u043b\u0430\u0442\u044c \u043d\u0435 \u043d\u0443\u0436\u043d\u043e, \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u0438\u0442\u044c \u0438\u0445 \u0432 \u043d\u0430\u0431\u043e\u0440 \u0442\u043e\u043a\u0435\u043d\u043e\u0432:<\/p>\n<pre><code class=\"rust\">let value = TokenStream::from_str(&amp;flag.value)?;<\/code><\/pre>\n<p>\u0412 Rust \u043d\u0435\u0442 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u043e\u0433\u043e \u0440\u0435\u0448\u0435\u043d\u0438\u044f \u0434\u043b\u044f \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u0438 \u0431\u0438\u0442\u043e\u0432\u044b\u0445 \u0444\u043b\u0430\u0433\u043e\u0432. \u041f\u043e \u0430\u043d\u0430\u043b\u043e\u0433\u0438\u0438 \u0441 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f\u043c\u0438, \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0441\u0435\u0432\u0434\u043e\u043d\u0438\u043c \u043d\u0430 \u0431\u0430\u0437\u043e\u0432\u044b\u0439 \u0442\u0438\u043f \u0438 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u044b \u0434\u043b\u044f \u043a\u0430\u0436\u0434\u043e\u0433\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f.<\/p>\n<pre><code class=\"rust\">pub fn generate_flags(flags: &amp;Flags) -> Result&lt;TokenStream, Error> {     let name = format_ident!(\"{}\", flags.name);     let base_type = map_c_type(&amp;flags.flags_type);     let mut values = vec![];     for flag in &amp;flags.flags {         let value = TokenStream::from_str(&amp;flag.value)?;         let flag = format_ident!(\"{}\", flag.name);         values.push(quote! {             pub const #flag: #name = #value;         })     }     Ok(quote! {         pub type #name = #base_type;         #(#values)*     }) }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043a\u043e\u0434\u0430 \u0431\u0438\u0442\u043e\u0432\u044b\u0445 \u0444\u043b\u0430\u0433\u043e\u0432:<\/p>\n<pre><code class=\"rust\">pub type FMOD_DEBUG_FLAGS = c_uint; pub const FMOD_DEBUG_TYPE_CODEC: FMOD_DEBUG_FLAGS = 0x00000400; pub const FMOD_DEBUG_TYPE_TRACE: FMOD_DEBUG_FLAGS = 0x00000800;<\/code><\/pre>\n<h3>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b<\/h3>\n<p>\u0414\u043b\u044f \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u044f FMOD \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u043e\u0431\u044b\u0447\u043d\u044b\u0435 Rust \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0441 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u043c\u0438 \u043f\u043e\u043b\u044f\u043c\u0438. \u0414\u043b\u044f \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u043d\u043e\u0439 \u0440\u0430\u0431\u043e\u0442\u044b \u043d\u0443\u0436\u043d\u043e \u0442\u043e\u043b\u044c\u043a\u043e \u0434\u043e\u0431\u0430\u0432\u0438\u0442\u044c \u043c\u0430\u0440\u043a\u0435\u0440 <code>#[repr(C)]<\/code>.<\/p>\n<pre><code class=\"rust\">pub fn generate_structure(structure: &amp;Structure) -> TokenStream {     let name = format_ident!(\"{}\", structure.name);     let fields = structure.fields.iter().map(generate_field);     let default = generate_structure_default(&amp;structure);      quote! {         #[repr(C)]         #[derive(Debug, Copy, Clone)]         pub struct #name {             #(#fields),*         }         #default     } }<\/code><\/pre>\n<p>\u041a\u0430\u0436\u0434\u043e\u0435 \u043f\u043e\u043b\u0435, \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u043e\u0435 \u0432 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0435, \u0438\u043c\u0435\u0435\u0442 \u0438\u043c\u044f \u0438 \u0442\u0438\u043f. \u0414\u043e\u0431\u0430\u0432\u043b\u0435\u043d\u0438\u0435 <code>pub<\/code> \u043a \u043f\u043e\u043b\u044e \u0434\u0435\u043b\u0430\u0435\u0442 \u0435\u0433\u043e \u0432\u0438\u0434\u0438\u043c\u044b\u043c \u0434\u043b\u044f \u043a\u043e\u0434\u0430 \u0432 \u0434\u0440\u0443\u0433\u0438\u0445 \u043c\u043e\u0434\u0443\u043b\u044f\u0445, \u0430 \u0442\u0430\u043a\u0436\u0435 \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u043d\u0430\u043f\u0440\u044f\u043c\u0443\u044e \u043e\u0431\u0440\u0430\u0449\u0430\u0442\u044c\u0441\u044f \u043a \u043d\u0435\u043c\u0443.<\/p>\n<pre><code class=\"rust\">pub fn generate_field(field: &amp;Field) -> TokenStream {     let name = format_rust_ident(&amp;field.name);     let field_type = format_rust_type(         &amp;field.field_type,         &amp;field.as_const,         &amp;field.pointer,         &amp;field.array(),     );        quote! {         pub #name: #field_type     } }<\/code><\/pre>\n<p>\u0414\u043b\u044f \u0437\u0430\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0445 \u0438\u0437 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 FMOD \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u043f\u043e \u0441\u0441\u044b\u043b\u043a\u0435 \u043d\u0443\u0436\u0435\u043d \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0442\u043e\u0440, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0431\u044b \u0432\u044b\u0434\u0435\u043b\u044f\u043b \u043f\u0430\u043c\u044f\u0442\u044c \u043f\u043e\u0434 \u044d\u0442\u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u043d\u0430 \u0441\u0442\u043e\u0440\u043e\u043d\u0435 Rust. \u041d\u043e Rust \u043d\u0435 \u043c\u043e\u0436\u0435\u0442 \u0430\u0431\u0441\u0442\u0440\u0430\u0433\u0438\u0440\u043e\u0432\u0430\u0442\u044c\u0441\u044f \u043e\u0442 \u0432\u0441\u0435\u0433\u043e \u0447\u0442\u043e \u043c\u043e\u0436\u043d\u043e \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0432 \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0442\u043e\u0440\u0435, \u044d\u0442\u043e \u0441\u0438\u043b\u044c\u043d\u043e \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043e\u0442 \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u044b\u0445 \u0442\u0438\u043f\u043e\u0432. \u0414\u043b\u044f \u044d\u0442\u043e\u0433\u043e \u0431\u044b\u043b \u0441\u043e\u0437\u0434\u0430\u043d \u0442\u0438\u043f\u0430\u0436 <code>Default<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u043f\u043e \u0443\u043c\u043e\u043b\u0447\u0430\u043d\u0438\u044e:<\/p>\n<pre><code class=\"rust\">pub fn generate_structure_default(structure: &amp;Structure) -> TokenStream {     let name = format_ident!(\"{}\", structure.name);     let defaults = structure         .fields         .iter()         .map(|field| generate_field_default(&amp;structure.name, field));        quote! {         impl Default for #name {             fn default() -> Self {                 Self {                     #(#defaults),*                 }             }         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043a\u043e\u0434\u0430 \u043f\u0440\u043e\u0441\u0442\u043e\u0439 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b:<\/p>\n<pre><code class=\"rust\">#[repr(C)] #[derive(Debug, Copy, Clone)] pub struct FMOD_VECTOR {     pub x: c_float,     pub y: c_float,     pub z: c_float, }  impl Default for FMOD_VECTOR {     fn default() -> Self {         Self {             x: Default::default(),             y: Default::default(),             z: Default::default(),         }     } }<\/code><\/pre>\n<p>\u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u0442\u043e\u0442 \u0436\u0435 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0441, \u0447\u0442\u043e \u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0441 \u043a\u043b\u044e\u0447\u0435\u0432\u044b\u043c \u0441\u043b\u043e\u0432\u043e\u043c <code>union<\/code> \u0432\u043c\u0435\u0441\u0442\u043e <code>struct<\/code>:<\/p>\n<pre><code class=\"rust\">pub fn generate_structure_union(union: &amp;Union) -> TokenStream {     let fields = union.fields.iter().map(generate_field);     quote! {         #[repr(C)]         #[derive(Copy, Clone)]         pub union #name {             #(#fields),*         }     } }<\/code><\/pre>\n<p>\u0417\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u0432 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0435 \u043c\u043e\u0436\u043d\u043e \u043f\u043e\u043b\u0443\u0447\u0438\u0442\u044c \u0442\u0430\u043a\u0438\u043c \u0436\u0435 \u043e\u0431\u0440\u0430\u0437\u043e\u043c \u043a\u0430\u043a \u0438 \u043f\u0440\u0438 \u043e\u0431\u0440\u0430\u0449\u0435\u043d\u0438\u0438 \u043a \u043f\u043e\u043b\u044e:<\/p>\n<pre><code class=\"rust\">match &amp;structure.union {     Some(union) => {         let union_name = format_ident!(\"{}_UNION\", structure.name);         let union = generate_structure_union(&amp;union_name, union);         quote! {             #[repr(C)]             #[derive(Copy, Clone)]             pub struct #name {                 #(#fields),*,                 pub union: #union_name             }             #default             #union         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043a\u043e\u0434\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0441 \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u0435\u043c:<\/p>\n<pre><code class=\"rust\">#[repr(C)] #[derive(Copy, Clone)] pub struct FMOD_STUDIO_USER_PROPERTY {     pub name: *const c_char,     pub type_: FMOD_STUDIO_USER_PROPERTY_TYPE,     pub union: FMOD_STUDIO_USER_PROPERTY_UNION, }  #[repr(C)] #[derive(Copy, Clone)] pub union FMOD_STUDIO_USER_PROPERTY_UNION {     pub intvalue: c_int,     pub boolvalue: FMOD_BOOL,     pub floatvalue: c_float,     pub stringvalue: *const c_char, }<\/code><\/pre>\n<h3>\u0424\u0443\u043d\u043a\u0446\u0438\u0438<\/h3>\n<p>\u0414\u043b\u044f \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u043e\u0432, \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043e\u0442\u043e\u0440\u044b\u0445 Rust \u043c\u043e\u0436\u0435\u0442 \u0432\u044b\u0437\u044b\u0432\u0430\u0442\u044c \u0432\u043d\u0435\u0448\u043d\u0438\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043d\u0443\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0435 \u0441\u043b\u043e\u0432\u043e <code>extern<\/code> \u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u044c \u0441\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u0435 \u043e \u0432\u044b\u0437\u043e\u0432\u0430\u0445 ABI, \u0432 \u043d\u0430\u0448\u0435\u043c \u0441\u043b\u0443\u0447\u0430\u0435 <code>\u201cC\u201d<\/code> \u043f\u043e\u0442\u043e\u043c\u0443, \u0447\u0442\u043e \u043c\u044b \u0431\u0443\u0434\u0435\u043c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0443 FMOD \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u044e\u0449\u0443\u044e C API.<\/p>\n<p>\u0410\u0442\u0440\u0438\u0431\u0443\u0442 <code>#[link(name=libname)]<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043a\u043e\u043c\u043f\u043e\u043d\u043e\u0432\u0449\u0438\u043a\u0443 \u0441\u043b\u0438\u043d\u043a\u043e\u0432\u0430\u0442\u044c \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0443 <code>libname<\/code>. FMOD \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0434\u0432\u0435 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438: fmod, fmodstudio.<\/p>\n<pre><code class=\"rust\">pub fn generate_extern(link: &amp;String, api: &amp;Vec&lt;Function>) -> TokenStream {     let mut functions = api.iter().map(generate_function);     quote! {         #[link(name = #link)]         extern \"C\" {             #(#functions)*         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0438 \u0442\u0438\u043f\u043e\u0432 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432 \u0432\u043d\u0435\u0448\u043d\u0435\u0439 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440 Rust \u043d\u0435 \u043c\u043e\u0436\u0435\u0442 \u043f\u0440\u043e\u0432\u0435\u0440\u0438\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u0430\u044f \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u043e\u0432 \u043d\u0430 \u043e\u0441\u043d\u043e\u0432\u0435 \u0440\u0430\u0437\u043e\u0431\u0440\u0430\u043d\u043d\u044b\u0445 \u0434\u0430\u043d\u043d\u044b\u0445 API \u2014 \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0439 \u043c\u043e\u043c\u0435\u043d\u0442 \u0434\u043b\u044f \u043d\u0430\u0434\u0435\u0436\u043d\u043e\u0441\u0442\u0438 \u0438 \u0440\u0430\u0431\u043e\u0442\u043e\u0441\u043f\u043e\u0441\u043e\u0431\u043d\u043e\u0441\u0442\u0438 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438.<\/p>\n<pre><code class=\"rust\">pub fn generate_function(function: &amp;Function) -> TokenStream {     let name = format_ident!(\"{}\", function.name);     let arguments = function.arguments.iter().map(generate_argument);     let return_type = map_c_type(&amp;function.return_type);     quote! {         pub fn #name(#(#arguments),*) -> #return_type;     } } <\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u0438:<\/p>\n<pre><code class=\"rust\">#[link(name = \"fmod\")] extern \"C\" {     pub fn FMOD_System_GetCPUUsage(         system: *mut FMOD_SYSTEM,         usage: *mut FMOD_CPU_USAGE,     ) -> FMOD_RESULT; }<\/code><\/pre>\n<h2>\u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430<\/h2>\n<p>\u0427\u0442\u043e\u0431\u044b \u0441\u043e\u043e\u0431\u0449\u0438\u0442\u044c \u043e \u0441\u043e\u0431\u044b\u0442\u0438\u044f\u0445 \u0438\u043b\u0438 \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u043c \u0441\u043e\u0441\u0442\u043e\u044f\u043d\u0438\u0438 FMOD \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u043e\u043a\u043e\u043b\u043e \u0441\u043e\u0442\u043d\u0438 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430.<\/p>\n<p>\u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u044b\u0435 \u0432 Rust \u043c\u043e\u0436\u043d\u043e \u043f\u0435\u0440\u0435\u0434\u0430\u0432\u0430\u0442\u044c \u0432\u043e \u0432\u043d\u0435\u0448\u043d\u044e\u044e \u0421 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0443 \u043a\u0430\u043a \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430. \u0414\u043b\u044f \u044d\u0442\u043e\u0433\u043e \u043e\u043d\u0430 \u0434\u043e\u043b\u0436\u043d\u0430 \u0431\u044b\u0442\u044c \u043e\u0442\u043c\u0435\u0447\u0435\u043d\u0430 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0433\u043e \u0441\u043b\u043e\u0432\u0430 <code>extern<\/code> \u0441 \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u044b\u043c \u0441\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u0435\u043c \u043e \u0432\u044b\u0437\u043e\u0432\u0430\u0445 <code>\u201cC\u201d<\/code>, \u0447\u0442\u043e\u0431\u044b \u0435\u0435 \u043c\u043e\u0436\u043d\u043e \u0431\u044b\u043b\u043e \u0432\u044b\u0437\u0432\u0430\u0442\u044c \u0438\u0437 C \u043a\u043e\u0434\u0430.<\/p>\n<p>\u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0442\u0438\u043f\u044b Rust \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u044b \u0442\u0430\u043a, \u0447\u0442\u043e\u0431\u044b \u043d\u0438\u043a\u043e\u0433\u0434\u0430 \u043d\u0435 \u0431\u044b\u0442\u044c \u043d\u0443\u043b\u0435\u0432\u044b\u043c\u0438, \u0432 \u0442\u043e\u043c \u0447\u0438\u0441\u043b\u0435 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u043d\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u0438. \u041d\u043e \u043f\u0440\u0438 \u0432\u0437\u0430\u0438\u043c\u043e\u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0438 \u0441 FMOD C API \u0434\u043e\u043f\u0443\u0441\u043a\u0430\u0435\u0442\u0441\u044f \u0447\u0442\u043e \u044d\u0442\u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u043c\u043e\u0433\u0443\u0442 \u0431\u044b\u0442\u044c \u043d\u0443\u043b\u0435\u0432\u044b\u043c\u0438. \u042d\u0442\u043e \u0440\u0430\u0441\u043f\u0440\u043e\u0441\u0442\u0440\u0430\u043d\u0435\u043d\u043d\u0430\u044f \u0438\u0441\u0442\u043e\u0440\u0438\u044f, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0432 Rust \u0435\u0441\u0442\u044c \u0440\u0435\u0448\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0443\u043f\u0440\u043e\u0449\u0430\u0435\u0442 \u0440\u0430\u0431\u043e\u0442\u0443, \u043d\u0435 \u043f\u0440\u0438\u0431\u0435\u0433\u0430\u044f \u043a \u043d\u0435\u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u043c\u0443 \u043a\u043e\u0434\u0443 \u0438 \u0440\u0443\u0447\u043d\u044b\u043c \u043c\u0430\u043d\u0438\u043f\u0443\u043b\u044f\u0446\u0438\u044f\u043c \u0441 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f\u043c\u0438 \u2014 \u043f\u0441\u0435\u0432\u0434\u043e\u043d\u0438\u043c \u043d\u0430 \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u044b\u0439 \u0442\u0438\u043f <code>Option&lt;unsafe extern fn(...)><\/code> \u0433\u0434\u0435 <code>None<\/code> \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u0435\u0442 \u043d\u0443\u043b\u0435\u0432\u043e\u043c\u0443 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044e.<\/p>\n<p>\u0412 C \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043c\u043e\u0433\u0443\u0442 \u043f\u0440\u0438\u043d\u0438\u043c\u0430\u0442\u044c \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u043e\u0435 \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432. \u042d\u0442\u043e\u0433\u043e \u043c\u043e\u0436\u043d\u043e \u0434\u043e\u0431\u0438\u0442\u044c\u0441\u044f \u0438 \u0432 Rust, \u0443\u043a\u0430\u0437\u0430\u0432 <code>...<\/code> \u0432 \u0441\u043f\u0438\u0441\u043a\u0435 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u0432\u043d\u0435\u0448\u043d\u0435\u0439 \u0444\u0443\u043d\u043a\u0446\u0438\u0438:<\/p>\n<pre><code class=\"rust\">pub fn generate_callback(callback: &amp;Callback) -> TokenStream {     let name = format_ident!(\"{}\", callback.name);     let arguments = callback.arguments.iter().map(generate_argument);     let varargs = if callback.varargs.is_some() {       Some(quote! {, ...})     } else {       None     };     let return_type = if let Some(return_type) = callback.returns() {       Some(quote! { -> #return_type })     } else {       None     };      quote! {         pub type #name = Option&lt;           unsafe extern \"C\" fn(           #(#arguments),* #varargs           ) #return_type         >;     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f \u043d\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u044e \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0433\u043e \u0432\u044b\u0437\u043e\u0432\u0430:<\/p>\n<pre><code class=\"rust\">pub type FMOD_CODEC_FILE_SEEK_FUNC = Option&lt;     unsafe extern \"C\" fn(         codec_state: *mut FMOD_CODEC_STATE,         pos: c_uint,         method: FMOD_CODEC_SEEK_METHOD,     ) -> FMOD_RESULT; >;<\/code><\/pre>\n<h3>\u041c\u0430\u043f\u043f\u0438\u043d\u0433 FFI \u0442\u0438\u043f\u043e\u0432<\/h3>\n<p>\u0418\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 FMOD \u0435\u0441\u0442\u0435\u0441\u0442\u0432\u0435\u043d\u043d\u043e \u043d\u0435 \u043e\u0431\u0445\u043e\u0434\u0438\u0442\u0441\u044f \u0431\u0435\u0437 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u0431\u0430\u0437\u043e\u0432\u044b\u0445 \u0442\u0438\u043f\u043e\u0432 C, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043d\u0435 \u0442\u0430\u043a \u043f\u043e\u0434\u0440\u043e\u0431\u043d\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u044b \u043a\u0430\u043a \u0442\u0438\u043f\u044b Rust. \u0427\u0442\u043e\u0431\u044b \u043c\u0430\u043f\u043f\u0438\u043d\u0433 \u0431\u044b\u043b \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u044b\u043c, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u043f\u0441\u0435\u0432\u0434\u043e\u043d\u0438\u043c\u044b \u0438\u0437 \u043c\u043e\u0434\u0443\u043b\u044f <code>std::os:raw<\/code>.<\/p>\n<p>\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0435 \u0442\u0438\u043f\u044b FMOD \u0442\u0430\u043a \u0438\u043b\u0438 \u0438\u043d\u0430\u0447\u0435 \u043f\u0435\u0440\u0435\u0434\u0430\u044e\u0442\u0441\u044f \u0432 FFI \u0431\u0435\u0437 \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0439, \u0431\u043b\u0430\u0433\u043e\u0434\u0430\u0440\u044f \u0431\u043b\u0438\u0437\u043e\u0441\u0442\u0438 Rust \u043a \u0441\u0438\u0441\u0442\u0435\u043c\u043d\u043e\u043c\u0443 \u0443\u0440\u043e\u0432\u043d\u044e \u0438 C \u0432 \u0447\u0430\u0441\u0442\u043d\u043e\u0441\u0442\u0438. \u041f\u043e\u044d\u0442\u043e\u043c\u0443 \u0432\u0441\u0435 \u0447\u0442\u043e \u043d\u0430\u043c \u043d\u0443\u0436\u043d\u043e, \u044d\u0442\u043e \u043f\u0440\u0430\u0432\u0438\u043b\u044c\u043d\u043e \u0443\u043a\u0430\u0437\u0430\u0442\u044c \u0438\u043c\u044f \u0442\u0438\u043f\u0430, \u043c\u0430\u043f\u043f\u0438\u043d\u0433 \u043d\u0435 \u0442\u0440\u0435\u0431\u0443\u0435\u0442\u0441\u044f:<\/p>\n<pre><code class=\"rust\">pub fn map_c_type(c_type: &amp;Type) -> TokenStream {     let name = match c_type {         FundamentalType(name) => {             let name = name.replace(\"unsigned\", \"u\").replace(\" \", \"\");             format_ident!(\"c_{}\", name)         }         Type::UserType(name) => format_ident!(\"{}\", name),     };     quote! { #name } }<\/code><\/pre>\n<p>\u0410\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438 \u043f\u043e\u043b\u044f \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u043c\u043e\u0433\u0443\u0442 \u0431\u044b\u0442\u044c \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f\u043c\u0438. \u0412 Rust \u043e\u043d\u0438 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u044b \u043a\u0430\u043a \u201c\u0441\u044b\u0440\u044b\u0435\u201d \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0446\u0438\u0439 <code>*mut T<\/code> \u0438 <code>*const T<\/code>.<\/p>\n<p>\u041a\u0440\u043e\u043c\u0435 \u0442\u043e\u0433\u043e, \u0432 C \u043c\u043e\u0436\u043d\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0430 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c. \u041f\u0435\u0440\u0432\u044b\u0439 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f \u0434\u043b\u044f \u0445\u0440\u0430\u043d\u0435\u043d\u0438\u044f \u0430\u0434\u0440\u0435\u0441\u0430 \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u043e\u0439, \u0432\u0442\u043e\u0440\u043e\u0439 \u0434\u043b\u044f \u0445\u0440\u0430\u043d\u0435\u043d\u0438\u044f \u0430\u0434\u0440\u0435\u0441\u0430 \u043f\u0435\u0440\u0432\u043e\u0433\u043e. \u0415\u0433\u043e \u0442\u0430\u043a \u0436\u0435 \u043d\u0430\u0437\u044b\u0432\u0430\u044e\u0442 \u201c\u0434\u0432\u043e\u0439\u043d\u044b\u043c \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0435\u043c\u201d:<\/p>\n<pre><code class=\"rust\">pub fn describe_pointer&lt;'a>( as_const: &amp;'a Option&lt;String>,  pointer: &amp;'a Option&lt;Pointer> ) -> &amp;'a str {     let description = match (as_const, pointer) {         (None, None) => \"\",         (None, Some(Pointer::NormalPointer(_))) => \"*mut\",         (None, Some(Pointer::DoublePointer(_))) => \"*mut *mut\",         (Some(_), Some(Pointer::NormalPointer(_))) => \"*const\",         (Some(_), Some(Pointer::DoublePointer(_))) => \"*const *const\",         (Some(_), None) => \"\",     };     description }<\/code><\/pre>\n<p>\u041c\u0430\u0441\u0441\u0438\u0432\u044b \u0432 Rust \u0442\u043e\u0436\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u044b, \u0435\u0433\u043e \u0440\u0430\u0437\u043c\u0435\u0440 \u0438 \u0442\u0438\u043f \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u043e\u0439 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u044e\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u0432\u0430\u0434\u0440\u0430\u0442\u043d\u044b\u0445 \u0441\u043a\u043e\u0431\u043e\u043a <code>[T; usize]<\/code>. FMOD \u0432 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0441\u043b\u0443\u0447\u0430\u044f\u0445 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u044b \u0434\u043b\u044f \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0440\u0430\u0437\u043c\u0435\u0440\u0430 \u043c\u0430\u0441\u0441\u0438\u0432\u0430. \u042d\u0442\u0438 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u044b \u0438\u043c\u0435\u044e\u0442 \u0442\u0438\u043f <code>unsigned int<\/code>, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u0440\u0438\u0432\u043e\u0434\u0438\u043c \u0438\u0445 \u043a \u0442\u0438\u043f\u0443 <code>as usize<\/code>, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f Rust.<\/p>\n<p>\u041f\u043e\u043b\u043d\u044b\u0439 \u043a\u043e\u0434 \u043c\u0430\u043f\u043f\u0438\u043d\u0433\u0430 \u0442\u0438\u043f\u043e\u0432 FFI:<\/p>\n<pre><code class=\"rust\">pub fn format_rust_type(     c_type: &amp;Type,     as_const: &amp;Option&lt;String>,     pointer: &amp;Option&lt;Pointer>,     as_array: &amp;Option&lt;TokenStream>, ) -> TokenStream {     let name = map_c_type(c_type);     let pointer = describe_pointer(as_const, pointer);     let rust_type = quote! { #pointer #name };     match as_array {         Some(dimension) => quote! { [#rust_type; #dimension as usize] },         None => rust_type,     } }<\/code><\/pre>\n<h2>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438<\/h2>\n<p>\u0415\u0441\u0442\u044c \u0434\u0432\u0435 \u043f\u0440\u0438\u0447\u0438\u043d\u044b \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u043e\u0432\u0430\u043d\u0438\u044f \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u043d\u0430\u0434 FFI \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f\u043c\u0438:<\/p>\n<ul>\n<li>\n<p>\u041e\u0431\u0451\u0440\u0442\u043a\u0430 \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0442\u043e\u043b\u044c\u043a\u043e \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0439 \u0432\u044b\u0441\u043e\u043a\u043e\u0443\u0440\u043e\u0432\u043d\u0435\u0432\u044b\u0439 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0438 \u0441\u043a\u0440\u044b\u0432\u0430\u0435\u0442 \u043d\u0435\u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u0435 \u0432\u043d\u0443\u0442\u0440\u0435\u043d\u043d\u0438\u0435 \u0434\u0435\u0442\u0430\u043b\u0438: \u0437\u0430\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u0435 \u043c\u0430\u0441\u0441\u0438\u0432\u0430 \u0438\u0437 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f, \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0430 C \u0441\u0442\u0440\u043e\u043a, \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0442\u0438\u043f\u043e\u0432, \u0438 \u043f\u0440\u043e\u0447\u0435\u0435.<\/p>\n<\/li>\n<li>\n<p>\u0421\u043e\u0433\u043b\u0430\u0448\u0435\u043d\u0438\u0435 \u043e\u0431 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u0438\u0438 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u043d\u044b\u0445 \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u043e\u0432. \u041d\u0430\u0437\u0432\u0430\u043d\u0438\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u0438 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 FMOD C API \u0434\u043b\u0438\u043d\u043d\u044b\u0435, \u0432\u043a\u043b\u044e\u0447\u0430\u044e\u0442 \u0432 \u0441\u0435\u0431\u044f \u0438\u0437\u0431\u044b\u0442\u043e\u0447\u043d\u0443\u044e \u0438\u043d\u0444\u043e\u0440\u043c\u0430\u0446\u0438\u044e \u043f\u043e \u043e\u0440\u0433\u0430\u043d\u0438\u0437\u0430\u0446\u0438\u0438 \u043a\u043e\u0434\u0430, \u0438 \u043f\u0440\u043e\u0441\u0442\u043e \u043d\u0435 \u0441\u043e\u0432\u043f\u0430\u0434\u0430\u044e\u0442 \u0441\u043e \u0441\u0442\u0438\u043b\u0435\u043c Rust \u043a\u043e\u0434\u0430. \u041d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u0442\u0438\u043f <code>FMOD_STUDIO_EVENTDESCRIPTION<\/code> \u0432 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0435 \u043c\u043e\u0436\u0435\u0442 \u0432\u044b\u0433\u043b\u044f\u0434\u0435\u0442\u044c \u0438 \u0447\u0438\u0442\u0430\u0442\u044c\u0441\u044f \u043f\u0440\u043e\u0449\u0435 \u043a\u0430\u043a <code>EventDescription<\/code><\/p>\n<\/li>\n<\/ul>\n<p>\u041f\u0440\u043e\u0446\u0435\u0441\u0441 \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0438 \u0441\u0432\u043e\u0434\u0438\u0442\u0441\u044f \u043a \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044e \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c\u0430 \u043a\u0432\u0430\u0437\u0438-\u0446\u0438\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f \u043f\u043e \u0430\u043d\u0430\u043b\u043e\u0433\u0438\u0438 \u0441 \u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0435\u0439 FFI.<\/p>\n<h3>\u041d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u044b\u0435 \u0442\u0438\u043f\u044b<\/h3>\n<p>\u0412\u0441\u0435 \u043e\u0431\u044a\u0435\u043a\u0442\u044b FMOD \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442\u0441\u044f \u0432 \u0432\u0438\u0434\u0435 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f \u043d\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443. \u0418\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u044d\u0442\u0438\u0445 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0435\u0439 \u0432\u044b\u0445\u043e\u0434\u0438\u0442 \u0437\u0430 \u0440\u0430\u043c\u043a\u0438 \u043c\u043e\u0434\u0435\u043b\u0438 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0439 \u0440\u0430\u0431\u043e\u0442\u044b Rust. \u0414\u043b\u044f \u043a\u0430\u0436\u0434\u043e\u0433\u043e \u0442\u0430\u043a\u043e\u0433\u043e \u043e\u0431\u044a\u0435\u043a\u0442\u0430 \u0441\u043e\u0437\u0434\u0430\u0434\u0438\u043c \u043e\u0431\u0451\u0440\u0442\u043a\u0443, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0431\u0443\u0434\u0435\u0442 \u0441\u043a\u0440\u044b\u0432\u0430\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u0443 \u0441 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0435\u043c.<\/p>\n<pre><code class=\"rust\">pub fn generate_opaque_type( key: &amp;String,  methods: &amp;Vec&lt;&amp;Function>,  api: &amp;Api ) -> TokenStream {     let name = format_struct_ident(key);     let opaque_type = format_ident!(\"{}\", key);      quote! {         #[derive(Debug, Clone, Copy)]         pub struct #name {             pointer: *mut ffi::#opaque_type,         }          impl #name {             pub fn from(pointer: *mut ffi::#opaque_type) -> Self {                 Self { pointer }             }             pub fn as_mut_ptr(&amp;self) -> *mut ffi::#opaque_type {                 self.pointer             }         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 Rust \u043e\u0431\u044a\u0435\u043a\u0442\u0430:<\/p>\n<pre><code class=\"rust\">#[derive(Debug, Clone, Copy)] pub struct EventDescription {     pointer: *mut ffi::FMOD_STUDIO_EVENTDESCRIPTION, }  impl EventDescription {     pub fn from(pointer: *mut ffi::FMOD_STUDIO_EVENTDESCRIPTION) -> Self {         Self { pointer }     }     pub fn as_mut_ptr(&amp;self) -> *mut ffi::FMOD_STUDIO_EVENTDESCRIPTION {         self.pointer     } }<\/code><\/pre>\n<h3>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f<\/h3>\n<p>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0432 Rust \u043e\u0442\u043b\u0438\u0447\u0430\u044e\u0442\u0441\u044f \u043e\u0442 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0439 \u0432 C. \u0424\u0430\u043a\u0442\u0438\u0447\u0435\u0441\u043a\u0438 \u044d\u0442\u043e \u043d\u0435 \u043d\u0430\u0431\u043e\u0440 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u044b\u0445 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442, \u0430 \u0430\u043b\u0433\u0435\u0431\u0440\u0430\u0438\u0447\u0435\u0441\u043a\u0438\u0439 \u0442\u0438\u043f \u0434\u0430\u043d\u043d\u044b\u0445. \u041d\u0443\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0435 \u0441\u043b\u043e\u0432\u043e <code>enum<\/code>, \u0447\u0442\u043e\u0431\u044b \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0442\u0438\u043f \u0438 \u043d\u0430\u0431\u043e\u0440 \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0431\u0443\u0434\u0443\u0442 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u043e\u0432\u0430\u0442\u044c \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f\u043c.<\/p>\n<p>FMOD \u0447\u0430\u0441\u0442\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u043e\u0442\u0440\u0438\u0446\u0430\u0442\u0435\u043b\u044c\u043d\u044b\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0432 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f\u0445. \u0421\u043f\u0435\u0446\u0438\u0430\u043b\u044c\u043d\u043e \u0434\u0430\u0436\u0435 \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u044e\u0442 \u0437\u0430\u043a\u0440\u044b\u0432\u0430\u044e\u0449\u0438\u0439 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044c <code>_FORCEINT<\/code>  \u0441\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435\u043c <code>65536<\/code> \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0437\u0430\u0442\u0435\u043c \u043d\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f, \u043d\u043e \u0437\u0430\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440 \u0421 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0442\u0438\u043f \u0437\u043d\u0430\u043a\u043e\u0432\u043e\u0433\u043e \u0447\u0438\u0441\u043b\u0430. \u042d\u0442\u0438 \u0442\u0435\u0445\u043d\u0438\u0447\u0435\u0441\u043a\u0438\u0435 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u0438 \u043f\u0440\u043e\u043f\u0443\u0441\u043a\u0430\u0435\u043c, \u0447\u0442\u043e\u0431\u044b \u0441\u0434\u0435\u043b\u0430\u0442\u044c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u0435 Rust \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0439 \u0443\u0434\u043e\u0431\u043d\u0435\u0435.<\/p>\n<pre><code class=\"rust\">pub fn generate_enumeration(enumeration: &amp;Enumeration) -> TokenStream {     let name = format_struct_ident(&amp;enumeration.name);     let mut variants = vec![];     for enumerator in &amp;enumeration.enumerators {         if enumerator.name.ends_with(\"FORCEINT\") {             continue;         }         let variant = format_variant(&amp;enumeration.name, &amp;enumerator.name);         variants.push(variant);     }     quote! {         #[derive(Debug, Clone, Copy, PartialEq)]         pub enum #name {             #(#variants),*         }     } }<\/code><\/pre>\n<p>\u0414\u043b\u044f \u0442\u043e\u0433\u043e \u0447\u0442\u043e\u0431\u044b \u043f\u0435\u0440\u0435\u0434\u0430\u0442\u044c \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 Rust \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0432 FFI \u0444\u0443\u043d\u043a\u0446\u0438\u0438, \u043d\u0443\u0436\u043d\u043e \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435. \u0422\u0438\u043f\u0430\u0436 <code>From<\/code> \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u0442\u0438\u043f\u0443 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c, \u043a\u0430\u043a \u0441\u043e\u0437\u0434\u0430\u0442\u044c \u0441\u0435\u0431\u044f \u0438\u0437 \u0434\u0440\u0443\u0433\u043e\u0433\u043e \u0442\u0438\u043f\u0430, \u0442\u0435\u043c \u0441\u0430\u043c\u044b\u043c \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u044f. \u0410 \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0435 \u0441\u043b\u043e\u0432\u043e <code>match<\/code> \u0440\u0435\u0430\u043b\u0438\u0437\u0443\u0435\u0442 \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c \u0441\u043e\u043f\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u0441 \u043e\u0431\u0440\u0430\u0437\u0446\u043e\u043c, \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u0432 \u0434\u0430\u043d\u043d\u043e\u043c \u0441\u043b\u0443\u0447\u0430\u0435 \u0434\u043b\u044f \u043a\u0430\u0436\u0434\u043e\u0433\u043e \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u0430 Rust \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0443\u044e\u0449\u0438\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 FFI \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f.<\/p>\n<pre><code class=\"rust\">enumerator_arms.push(quote! { #name::#variant => ffi::#enumerator });  ...  impl From&lt;#name> for ffi::#enumeration {     fn from(value: #name) -> ffi::#enumeration {         match value {             #(#enumerator_arms),*         }     } }<\/code><\/pre>\n<p>\u041e\u0434\u0438\u043d \u0438\u0437 \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c\u043e\u0432 \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0439 \u0440\u0430\u0431\u043e\u0442\u044b \u0437\u0430\u043a\u043b\u044e\u0447\u0430\u0435\u0442\u0441\u044f \u0432 \u0442\u043e\u043c, \u0447\u0442\u043e Rust \u043e\u0431\u0435\u0441\u043f\u0435\u0447\u0438\u0432\u0430\u0435\u0442 \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0443 \u043f\u043e\u043b\u043d\u043e\u0442\u044b \u0441\u043e\u043f\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u0432\u0430\u0440\u0438\u0430\u043d\u0442\u043e\u0432 \u0432 \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0446\u0438\u0438 <code>match<\/code>. \u041d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440 \u0434\u0435\u043b\u0430\u0435\u0442 \u0432\u044b\u0432\u043e\u0434, \u0447\u0442\u043e FFI \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0435 <code>FMOD_PLUGINTYPE<\/code> \u043c\u043e\u0436\u0435\u0442 \u0438\u043c\u0435\u0442\u044c \u043b\u044e\u0431\u043e\u0435 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435. \u0421\u0438\u043c\u0432\u043e\u043b \u043f\u043e\u0434\u0447\u0435\u0440\u043a\u0438\u0432\u0430\u043d\u0438\u044f <code>_<\/code> \u0437\u0430\u0445\u0432\u0430\u0442\u044b\u0432\u0430\u0435\u0442 \u0432\u0441\u0435 \u043d\u0435 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0438 \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u0430\u0442\u044c \u043e\u0448\u0438\u0431\u043a\u0443 \u0431\u0435\u0437 \u0438\u0441\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0439, \u0432 \u0441\u043b\u0443\u0447\u0430\u0435 \u0435\u0441\u043b\u0438 FMOD \u0432\u0435\u0440\u043d\u0435\u0442 \u043d\u0435\u043e\u0436\u0438\u0434\u0430\u043d\u043d\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435:<\/p>\n<pre><code class=\"rust\">variant_arms.push(quote! { ffi::#enumerator => Ok(#name::#variant) });  ...  impl #name {     pub fn from(value: ffi::#enumeration) -> Result&lt;#name, Error> {         match value {             #(#variant_arms),*,             _ => Err(err_enum!(#enumeration_name, value)),         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 Rust \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f:<\/p>\n<pre><code class=\"rust\">#[derive(Debug, Clone, Copy, PartialEq)] pub enum PluginType {     Output,     Codec,     Dsp,     Max, } impl From&lt;PluginType> for ffi::FMOD_PLUGINTYPE {     fn from(value: PluginType) -> ffi::FMOD_PLUGINTYPE {         match value {             PluginType::Output => ffi::FMOD_PLUGINTYPE_OUTPUT,             PluginType::Codec => ffi::FMOD_PLUGINTYPE_CODEC,             PluginType::Dsp => ffi::FMOD_PLUGINTYPE_DSP,             PluginType::Max => ffi::FMOD_PLUGINTYPE_MAX,         }     } } impl PluginType {     pub fn from(value: ffi::FMOD_PLUGINTYPE) -> Result&lt;PluginType, Error> {         match value {             ffi::FMOD_PLUGINTYPE_OUTPUT => Ok(PluginType::Output),             ffi::FMOD_PLUGINTYPE_CODEC => Ok(PluginType::Codec),             ffi::FMOD_PLUGINTYPE_DSP => Ok(PluginType::Dsp),             ffi::FMOD_PLUGINTYPE_MAX => Ok(PluginType::Max),             _ => Err(err_enum!(\"FMOD_PLUGINTYPE\", value)),         }     } }<\/code><\/pre>\n<h3>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b<\/h3>\n<p>\u0427\u0442\u043e\u0431\u044b \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0435 \u0441\u043b\u043e\u0432\u043e <code>struct<\/code> \u0438 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u0435. \u0417\u0430\u0442\u0435\u043c \u0432\u043d\u0443\u0442\u0440\u0438 \u0444\u0438\u0433\u0443\u0440\u043d\u044b\u0445 \u0441\u043a\u043e\u0431\u043e\u043a \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c \u0438\u043c\u0435\u043d\u0430 \u0438 \u0442\u0438\u043f\u044b \u043f\u043e\u043b\u0435\u0439, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0431\u0443\u0434\u0443\u0442 \u0431\u043e\u043b\u044c\u0448\u0435 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u043e\u0432\u0430\u0442\u044c \u0438\u0434\u0438\u043e\u043c\u0430\u0442\u0438\u0447\u043d\u043e\u043c\u0443 Rust.<\/p>\n<pre><code class=\"rust\">pub fn generate_structure_code( structure: &amp;Structure,  api: &amp;Api ) -> TokenStream {     let ident = format_ident!(\"{}\", structure.name);     let name = format_struct_ident(&amp;structure.name);     let mut field = structure         .fields         .iter()         .filter(|field| is_convertable(&amp;structure, field))         .map(|field| generate_field(structure, field, api));     let presets = generate_presets(structure, api);     let into = generate_structure_into(structure, api);     let try_from = generate_structure_try_from(structure, api);     quote! {         #[derive(Debug, Clone)]         pub struct #name {             #(#fields),*         }         #presets         #try_from         #into     } }<\/code><\/pre>\n<p>\u0414\u043b\u044f \u0442\u043e\u0433\u043e \u0447\u0442\u043e\u0431\u044b \u0437\u0430\u043f\u043e\u043b\u043d\u0438\u0442\u044c \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443 \u0438\u0437 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 FFI \u0444\u0443\u043d\u043a\u0446\u0438\u0439, \u043d\u0443\u0436\u043d\u043e \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435. \u0422\u0438\u043f\u0430\u0436 <code>TryFrom<\/code> \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u044f, \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u043f\u043e\u0434\u0440\u0430\u0437\u0443\u043c\u0435\u0432\u0430\u0435\u0442 \u0447\u0442\u043e \u043c\u043e\u0436\u0435\u0442 \u043f\u0440\u043e\u0438\u0437\u043e\u0439\u0442\u0438 \u043e\u0448\u0438\u0431\u043a\u0430. \u0410\u043a\u0442\u0443\u0430\u043b\u044c\u043d\u043e, \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u043c\u044b \u043d\u0435 \u043c\u043e\u0436\u0435\u043c \u0433\u0430\u0440\u0430\u043d\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u043d\u043e\u0441\u0442\u044c \u0440\u0430\u0431\u043e\u0442\u044b \u0432\u043d\u0435\u0448\u043d\u0435\u0439 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438.<\/p>\n<pre><code class=\"rust\">pub fn generate_structure_try_from( structure: &amp;Structure,  api: &amp;Api ) -> TokenStream {     let ident = format_ident!(\"{}\", structure.name);     let name = format_struct_ident(&amp;structure.name);     let conversion = structure         .fields         .iter()         .map(|field| generate_field_from(&amp;structure.name, field, api));     quote! {         impl TryFrom&lt;ffi::#ident> for #name {             type Error = Error;              fn try_from(value: ffi::#ident) -> Result&lt;Self, Self::Error> {                 unsafe {                     Ok(#name {                         #(#conversion),*                     })                 }             }         }     } }<\/code><\/pre>\n<p>\u0427\u0442\u043e\u0431\u044b \u043f\u0435\u0440\u0435\u0434\u0430\u0442\u044c \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0432 FFI \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u0440\u0435\u0430\u043b\u0438\u0437\u0443\u0435\u043c \u043e\u0431\u0440\u0430\u0442\u043d\u043e\u0435 \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0442\u0438\u043f\u0430\u0436\u0430 <code>Into<\/code>.<\/p>\n<pre><code class=\"rust\">pub fn generate_structure_into( structure: &amp;Structure,  api: &amp;Api ) -> TokenStream {     let ident = format_ident!(\"{}\", structure.name);     let name = format_struct_ident(&amp;structure.name);     let conversion = &amp;structure         .fields         .iter()         .map(|field| generate_field_into(&amp;structure.name, field, api));     quote! {         impl Into&lt;ffi::#ident> for #name {             pub fn into(self) -> ffi::#ident {                 ffi::#ident {                     #(#conversion),*                 }             }         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 Rust \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b:<\/p>\n<pre><code class=\"rust\">#[derive(Debug, Clone)] pub struct Vector {     pub x: f32,     pub y: f32,     pub z: f32, }  impl TryFrom&lt;ffi::FMOD_VECTOR> for Vector {     type Error = Error;     fn try_from(value: ffi::FMOD_VECTOR) -> Result&lt;Self, Self::Error> {         unsafe {             Ok(Vector {                 x: value.x,                 y: value.y,                 z: value.z,             })         }     } }  impl Into&lt;ffi::FMOD_VECTOR> for Vector {     fn into(self) -> ffi::FMOD_VECTOR {         ffi::FMOD_VECTOR {             x: self.x,             y: self.y,             z: self.z,         }     } }<\/code><\/pre>\n<h3>\u041c\u0435\u0442\u043e\u0434\u044b<\/h3>\n<p>\u041f\u0440\u0430\u043a\u0442\u0438\u0447\u0435\u0441\u043a\u0438 \u0432\u0441\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 FMOD \u2014 \u043c\u0435\u0442\u043e\u0434\u044b, \u0442\u043e \u0435\u0441\u0442\u044c \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0441\u0432\u044f\u0437\u0430\u043d\u044b \u0441 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u044b\u043c \u0442\u0438\u043f\u043e\u043c \u043e\u0431\u044a\u0435\u043a\u0442\u043e\u0432 \u0438 \u0432\u044b\u0437\u044b\u0432\u0430\u044e\u0442\u0441\u044f \u0434\u043b\u044f \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u043e\u0433\u043e \u044d\u043a\u0437\u0435\u043c\u043f\u043b\u044f\u0440\u0430 \u044d\u0442\u043e\u0433\u043e \u0442\u0438\u043f\u0430.<\/p>\n<p>\u0412\u0441\u0435 \u043c\u0435\u0442\u043e\u0434\u044b \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442 \u0441\u0442\u0430\u0442\u0443\u0441 \u043a\u043e\u0434 <code>FMOD_RESULT<\/code> \u2014 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u043e\u0435 \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0435 \u043a\u043e\u0434\u043e\u0432 \u043e\u0448\u0438\u0431\u043e\u043a. \u042d\u0442\u0438 \u043e\u0448\u0438\u0431\u043a\u0438 \u0440\u0430\u0441\u0448\u0438\u0444\u0440\u0443\u0435\u043c \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043c\u0430\u043a\u0440\u043e\u0441\u0430 <code>err_fmod!<\/code> \u0438 \u043f\u0440\u0438\u0432\u0435\u0434\u0435\u043c \u043a \u0442\u0438\u043f\u0443 <code>Result&lt;T,E><\/code> \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f \u0432 Rust \u0434\u043b\u044f \u0440\u0430\u0431\u043e\u0442\u044b \u0441 \u043e\u0448\u0438\u0431\u043a\u0430\u043c\u0438.<\/p>\n<pre><code class=\"rust\">macro_rules! err_fmod {     ($ function : expr , $ code : expr) => {         Error::Fmod {             function: $function.to_string(),             code: $code,             message: ffi::map_fmod_error($code).to_string(),         }     }; }  pub fn map_fmod_error(result: FMOD_RESULT) -> &amp;'static str {     match result {         FMOD_OK => \"No errors.\",         FMOD_ERR_FILE_BAD => \"Error loading file.\",         \/\/ ...     } }<\/code><\/pre>\n<p>\u0412\u043d\u0435\u0448\u043d\u0438\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u0441\u0447\u0438\u0442\u0430\u044e\u0442\u0441\u044f \u043d\u0435\u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u044b\u043c\u0438, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u0432\u044b\u0437\u043e\u0432\u044b \u043a \u043d\u0438\u043c \u0434\u043e\u043b\u0436\u043d\u044b \u0431\u044b\u0442\u044c \u0437\u0430\u043a\u043b\u044e\u0447\u0435\u043d\u044b \u0432 <code>unsafe<\/code> \u043a\u0430\u043a \u043e\u0431\u0435\u0449\u0430\u043d\u0438\u0435 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440\u0443 Rust, \u0447\u0442\u043e \u0432\u0441\u0435, \u0447\u0442\u043e \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442\u0441\u044f \u0432\u043d\u0443\u0442\u0440\u0438, \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0442\u0435\u043b\u044c\u043d\u043e \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e. \u042d\u0442\u043e \u043e\u0434\u0438\u043d \u0438\u0437 \u043a\u043b\u044e\u0447\u0435\u0432\u044b\u0445 \u043c\u043e\u043c\u0435\u043d\u0442\u043e\u0432 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f Rust \u043e\u0431\u0435\u0440\u0442\u043a\u0438.<\/p>\n<pre><code class=\"rust\">pub fn generate_method(     owner: &amp;str,      function: &amp;Function,      api: &amp;Api ) -> TokenStream {     let mut signature = Signature::new();      for argument in &amp;function.arguments { ... }      let (arguments, inputs, out, output, returns) = signature.define();     let method_name = extract_method_name(&amp;function.name);     let method = format_ident!(\"{}\", method_name);     let function_name = &amp;function.name;     let function = format_ident!(\"{}\", function_name);      quote! {         pub fn #method( #(#arguments),* ) -> Result&lt;#returns, Error> {             unsafe {                 #(#out)*                 match ffi::#function( #(#inputs),* ) {                     ffi::FMOD_OK => Ok(#output),                     error => Err(err_fmod!(#function_name, error)),                 }             }         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043c\u0435\u0442\u043e\u0434\u0430:<\/p>\n<pre><code class=\"rust\">impl System {     pub fn get_cpu_usage(&amp;self) -> Result&lt;CpuUsage, Error> {         unsafe {             let mut usage = ffi::FMOD_CPU_USAGE::default();             match ffi::FMOD_System_GetCPUUsage(self.pointer, &amp;mut usage) {                 ffi::FMOD_OK => Ok(CpuUsage::from(usage)?),                 error => Err(err_fmod!(\"FMOD_System_GetCPUUsage\", error)),             }         }     } }<\/code><\/pre>\n<h3>\u041f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u043e\u0432 \u043c\u0435\u0442\u043e\u0434\u043e\u0432<\/h3>\n<p>\u0412 \u043e\u0431\u0449\u0435\u043c \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b \u043c\u043e\u0436\u043d\u043e \u0440\u0430\u0437\u0434\u0435\u043b\u0438\u0442\u044c \u043d\u0430 \u0442\u0440\u0438 \u0442\u0438\u043f\u0430:<\/p>\n<ul>\n<li>\n<p>\u0412\u0445\u043e\u0434\u044f\u0449\u0438\u0435 \u0434\u0430\u043d\u043d\u044b\u0435<\/p>\n<\/li>\n<li>\n<p>\u041e\u043f\u0446\u0438\u043e\u043d\u0430\u043b\u044c\u043d\u044b\u0435 \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0435 \u0434\u0430\u043d\u043d\u044b\u0435<\/p>\n<\/li>\n<li>\n<p>\u0412\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0435 \u0434\u0430\u043d\u043d\u044b\u0435<\/p>\n<\/li>\n<\/ul>\n<p>\u0414\u043b\u044f \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0445 \u0434\u0430\u043d\u043d\u044b\u0445 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e \u0443\u043a\u0430\u0437\u0430\u0442\u044c \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430 \u0432 \u0441\u0438\u0433\u043d\u0430\u0442\u0443\u0440\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 <code>param<\/code> \u0438 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430 \u0434\u043b\u044f \u043f\u0435\u0440\u0435\u0434\u0430\u0447\u0438 \u0432 FFI \u0444\u0443\u043d\u043a\u0446\u0438\u044e <code>input<\/code>.<\/p>\n<pre><code class=\"rust\">struct InArgument {     pub param: TokenStream,     pub input: TokenStream, }<\/code><\/pre>\n<p>\u041e\u043f\u0446\u0438\u043e\u043d\u0430\u043b\u044c\u043d\u044b\u0435 \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0435 \u0434\u0430\u043d\u043d\u044b\u0435, \u043a\u0430\u043a \u043f\u0440\u0430\u0432\u0438\u043b\u043e, \u0441\u0432\u044f\u0437\u0430\u043d\u044b \u0441 \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u043e\u0439 \u043d\u0443\u043b\u0435\u0432\u044b\u0445 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0435\u0439 \u0438 \u0432\u0441\u0451 \u0441\u0432\u043e\u0434\u0438\u0442\u0441\u044f \u043a \u043e\u0431\u0435\u0440\u0442\u043a\u0435 \u0442\u0438\u043f\u043e\u0432 \u0432 <code>Option&lt;T><\/code> \u0432 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u0445 <code>param<\/code> \u0438 <code>input<\/code>.<\/p>\n<p>FMOD \u0432\u0441\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u0447\u0435\u0440\u0435\u0437 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438. \u041f\u043e\u044d\u0442\u043e\u043c\u0443 \u0434\u043b\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0445 \u0434\u0430\u043d\u043d\u044b\u0445 \u0432 \u043f\u0435\u0440\u0432\u0443\u044e \u043e\u0447\u0435\u0440\u0435\u0434\u044c \u043d\u0443\u0436\u043d\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u043f\u0435\u0440\u0435\u043c\u0435\u043d\u043d\u0443\u044e <code>target<\/code>, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0431\u0443\u0434\u0435\u0442 \u0441\u043e\u0434\u0435\u0440\u0436\u0430\u0442\u044c \u0443\u0447\u0430\u0441\u0442\u043e\u043a \u043f\u0430\u043c\u044f\u0442\u0438, \u0446\u0435\u043b\u0435\u0432\u043e\u0439 \u0434\u043b\u044f \u0437\u0430\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u044f \u0447\u0435\u0440\u0435\u0437 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c. \u0412\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u0434\u043b\u044f \u043f\u0435\u0440\u0435\u0434\u0430\u0447\u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f <code>source<\/code>. \u041f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u043e\u0433\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f <code>output<\/code> \u0432 \u043f\u043e\u0434\u0445\u043e\u0434\u044f\u0449\u0438\u0439 Rust \u0442\u0438\u043f. \u0418 \u0441\u0430\u043c\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u0442\u0438\u043f\u0430 \u0432 \u0441\u0438\u0433\u043d\u0430\u0442\u0443\u0440\u0435 \u043c\u0435\u0442\u043e\u0434\u0430 <code>retype<\/code>.<\/p>\n<pre><code class=\"rust\">struct OutArgument {     pub target: TokenStream,     pub source: TokenStream,     pub output: TokenStream,     pub retype: TokenStream, }<\/code><\/pre>\n<p>\u0422\u0430\u043a \u0447\u0442\u043e \u0434\u043b\u044f \u043a\u0430\u0436\u0434\u043e\u0433\u043e \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c \u0435\u0433\u043e \u0442\u0438\u043f (\u043c\u043e\u0434\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440) \u0438 \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u044b\u0439 \u043d\u0430\u0431\u043e\u0440 Rust \u043a\u043e\u0434\u0430:<\/p>\n<pre><code class=\"rust\">if !signature.overwrites(owner, function, argument) {     match api.get_modifier(&amp;function.name, &amp;argument.name) {         Modifier::None => signature += map_input(argument, api),         Modifier::Opt => signature += map_optional(argument, api),         Modifier::Out => signature += map_output(argument, api),     } }<\/code><\/pre>\n<p>\u0412 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0441\u043b\u0443\u0447\u0430\u044f\u0445 \u043f\u0440\u043e\u0449\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0445\u0430\u0440\u0434\u043a\u043e\u0434, \u0442\u043e \u0435\u0441\u0442\u044c \u0432\u0440\u0443\u0447\u043d\u0443\u044e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0442\u044c \u0436\u0435\u043b\u0430\u0435\u043c\u044b\u0439 \u0440\u0435\u0437\u0443\u043b\u044c\u0442\u0430\u0442 \u0432 \u043a\u043e\u0434\u0435 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438, \u0432\u043c\u0435\u0441\u0442\u043e \u0442\u043e\u0433\u043e \u0447\u0442\u043e\u0431\u044b \u0440\u0430\u0437\u0440\u0430\u0431\u0430\u0442\u044b\u0432\u0430\u0442\u044c \u0441\u043b\u043e\u0436\u043d\u043e\u0435 \u043e\u0431\u0449\u0435\u0435 \u0440\u0435\u0448\u0435\u043d\u0438\u0435. \u042d\u0442\u043e\u0442 \u0445\u0430\u0440\u0434\u043a\u043e\u0434 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d \u0432 \u043c\u0435\u0442\u043e\u0434\u0435 overwrites. \u0422\u0430\u043c \u0436\u0435 \u043c\u043e\u0436\u043d\u043e \u043a\u043e\u0440\u0440\u0435\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 \u0443\u043f\u0440\u043e\u0449\u0430\u0442\u044c \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043c\u0435\u0442\u043e\u0434\u044b:<\/p>\n<pre><code class=\"rust\">pub fn overwrites( &amp;mut self,  owner: &amp;str,  function: &amp;Function,  argument: &amp;Argument ) -> bool {     if function.name == \"FMOD_Studio_System_Create\" &amp;&amp; argument.name == \"headerversion\" {         self.inputs.push(quote! { ffi::FMOD_VERSION });         return true;     }  ... }<\/code><\/pre>\n<p>\u041a\u043b\u044e\u0447\u0435\u0432\u043e\u0435 \u0441\u043b\u043e\u0432\u043e <code>self<\/code> \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u044d\u043a\u0437\u0435\u043c\u043f\u043b\u044f\u0440 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b, \u0434\u043b\u044f \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u0432\u044b\u0437\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u043c\u0435\u0442\u043e\u0434. \u0412\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 <code>&amp;self<\/code> \u044d\u0442\u043e \u0441\u043e\u043a\u0440\u0430\u0449\u0435\u043d\u0438\u0435 \u0434\u043b\u044f <code>self: &amp;Self<\/code>, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043e\u0437\u043d\u0430\u0447\u0430\u0435\u0442 \u0441\u0441\u044b\u043b\u043a\u0443 \u043d\u0430 \u0442\u0438\u043f \u0432 \u043a\u043e\u0442\u043e\u0440\u043e\u043c \u0440\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u0430\u043d \u043c\u0435\u0442\u043e\u0434. \u041d\u0430\u043b\u0438\u0447\u0438\u0435 <code>self<\/code> \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c \u0438\u0437 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u044f \u0442\u0438\u043f\u0430 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430 \u0438 \u043d\u0430\u0437\u0432\u0430\u043d\u0438\u044f \u0432\u043b\u0430\u0434\u0435\u043b\u044c\u0446\u0430 (\u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0434\u043b\u044f \u043a\u043e\u0442\u043e\u0440\u043e\u0439 \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u043c \u043c\u0435\u0442\u043e\u0434):<\/p>\n<pre><code class=\"rust\">if arguments.is_empty()  &amp;&amp; argument_type.is_user_type(owner)  &amp;&amp; pointer == \"*mut\"  {     arguments.push(quote! { &amp;self });     sources.push(quote! { self.pointer }); }<\/code><\/pre>\n<p>\u041f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u0445 \u0434\u0430\u043d\u043d\u044b\u0445 \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043e\u0442 C \u0442\u0438\u043f\u0430 \u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f:<\/p>\n<pre><code class=\"rust\">fn map_input(argument: &amp;Argument, api: &amp;Api) -> InArgument {   let pointer = ffi::describe_pointer(&amp;argument.as_const, &amp;argument.pointer);   let argument_type = &amp;argument.argument_type;   let argument = format_argument_ident(&amp;argument.name);   match argument_type {     FundamentalType(type_name) => {       match &amp;format!(\"{}:{}\", pointer, type_name)[..] {         \":float\" => InArgument {           param: quote! { #argument: f32 },           input: quote! { #argument },         },         \/\/ ...       },       UserType(type_name) => {         let rust_type = format_struct_ident(&amp;type_name);         let ident = format_ident!(\"{}\", type_name);         match (pointer, api.describe_user_type(&amp;type_name)) {           (\"*mut\", UserTypeDesc::OpaqueType) => InArgument {             param: quote! { #argument: #rust_type },             input: quote! { #argument.as_mut_ptr() },           },           \/\/ ...         }       }     }   } }<\/code><\/pre>\n<p>\u0412 Rust, \u0432 \u043e\u0442\u043b\u0438\u0447\u0438\u0438 \u043e\u0442 C, \u0441\u0442\u0440\u043e\u043a\u0430 \u043d\u0435 \u0437\u0430\u043a\u0430\u043d\u0447\u0438\u0432\u0430\u0435\u0442\u0441\u044f \u043d\u0430 <code>\\0<\/code>. \u041f\u043e\u044d\u0442\u043e\u043c\u0443 \u043c\u044b \u0434\u043e\u043b\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u044b\u0439 \u0442\u0438\u043f <code>CString<\/code> \u0434\u043b\u044f \u043f\u0440\u043e\u0432\u0435\u0440\u043a\u0438 \u043d\u0443\u043b\u044f \u0438 \u043e\u0442\u043f\u0440\u0430\u0432\u043b\u044f\u0442\u044c \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435 \u043a\u0430\u043a \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0430 \u0431\u043b\u043e\u043a \u043f\u0430\u043c\u044f\u0442\u0438 \u0432 \u043a\u043e\u0442\u043e\u0440\u043e\u043c \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442\u0441\u044f \u0441\u0442\u0440\u043e\u043a\u0430:<\/p>\n<pre><code class=\"rust\">\"*const:char\" => InArgument {     param: quote! { #argument: &amp;str },     input: quote! { CString::new(#argument)?.as_ptr() }, },<\/code><\/pre>\n<p>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u043f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u044b\u0432\u0430\u0435\u043c \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0440\u0430\u043d\u0435\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043d\u043e\u0433\u043e \u0442\u0438\u043f\u0430\u0436\u0430 <code>Into<\/code>:<\/p>\n<pre><code class=\"rust\">(\"\", UserTypeDesc::Enumeration) => InArgument {     param: quote! { #argument: #rust_type },     input: quote! { #argument.into() }, },<\/code><\/pre>\n<p>\u0412 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u0441\u043b\u0443\u0447\u0430\u044f\u0445 FMOD \u043e\u0436\u0438\u0434\u0430\u0435\u0442 \u043f\u0435\u0440\u0435\u0434\u0430\u0447\u0443 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u0447\u0435\u0440\u0435\u0437 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0435 \u043f\u043e\u0434\u0440\u0430\u0437\u0443\u043c\u0435\u0432\u0430\u044f \u043f\u043e\u0434 \u044d\u0442\u0438\u043c \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u0438\u044f \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 \u044d\u0442\u0438\u0445 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440. \u0414\u043b\u044f \u044d\u0442\u043e\u0433\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043d\u044b\u0439 \u043c\u0435\u0445\u0430\u043d\u0438\u0437\u043c Rust \u0441\u0441\u044b\u043b\u043e\u043a \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <code>&amp;<\/code> \u0438 <code>&amp;mut<\/code>:<\/p>\n<pre><code class=\"rust\">(\"*mut\", UserTypeDesc::Structure) => InArgument {     param: quote! { #argument: #rust_type },     input: quote! { &amp;mut #argument.into() }, }, (\"\", UserTypeDesc::Structure) => InArgument {     param: quote! { #argument: #rust_type },     input: quote! { #argument.into() }, },<\/code><\/pre>\n<p>\u0418\u043d\u043e\u0433\u0434\u0430 FMOD \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0434\u0438\u043d\u0430\u043c\u0438\u0447\u0435\u0441\u043a\u0438\u0439 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0432 \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u043c\u043e\u0436\u043d\u043e \u043f\u043e \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044e \u043f\u0435\u0440\u0435\u0434\u0430\u0442\u044c \u043b\u044e\u0431\u043e\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0435. \u0412 \u044d\u0442\u043e\u043c \u0441\u043b\u0443\u0447\u0430\u0435 \u043d\u0435 \u043e\u0431\u043e\u0439\u0442\u0438\u0441\u044c \u0431\u0435\u0437 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f \u0441\u044b\u0440\u044b\u0445 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0435\u0439 \u043d\u0430 <code>c_void<\/code>:<\/p>\n<pre><code class=\"rust\">\"*const:void\" => InArgument {     param: quote! { #argument: *const c_void },     input: quote! { #argument }, },<\/code><\/pre>\n<p>\u041f\u0440\u0438\u043c\u0435\u0440 \u043c\u0435\u0442\u043e\u0434\u0430 \u0441 \u0432\u0445\u043e\u0434\u044f\u0449\u0438\u043c\u0438 \u0434\u0430\u043d\u043d\u044b\u043c\u0438:<\/p>\n<pre><code class=\"rust\">pub fn set_parameter_float(&amp;self, index: i32, value: f32) -> Result&lt;(), Error> {     unsafe {         match ffi::FMOD_DSP_SetParameterFloat(self.pointer, index, value) {             ffi::FMOD_OK => Ok(()),             error => Err(err_fmod!(\"FMOD_DSP_SetParameterFloat\", error)),         }     } }<\/code><\/pre>\n<p>\u041f\u0440\u0435\u043e\u0431\u0440\u0430\u0437\u043e\u0432\u0430\u043d\u0438\u0435 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0445 \u0434\u0430\u043d\u043d\u044b\u0445 \u0437\u0430\u0432\u0438\u0441\u0438\u0442 \u043e\u0442 \u0442\u0438\u043f\u0430 \u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f:<\/p>\n<pre><code class=\"rust\">fn map_output(argument: &amp;Argument, api: &amp;Api) -> OutArgument {   let pointer = ffi::describe_pointer(&amp;argument.as_const, &amp;argument.pointer);   let arg = format_argument_ident(&amp;argument.name);   match &amp;argument.argument_type {     FundamentalType(type_name) => match &amp;format!(\"{}:{}\", pointer, type_name)[..] {       \"*mut:float\" => OutArgument {         target: quote! { let mut #arg = f32::default(); },         source: quote! { &amp;mut #arg },         output: quote! { #arg },         retype: quote! { f32 },       },       \/\/ ...     },     UserType(user_type) => {       let type_name = format_struct_ident(&amp;user_type);       let ident = format_ident!(\"{}\", user_type);       match (pointer, api.describe_user_type(&amp;user_type)) {         (\"*mut\", UserTypeDesc::Structure) => OutArgument {           target: quote! { let mut #arg = ffi::#ident::default(); },           source: quote! { &amp;mut #arg },           output: quote! { #type_name::try_from(#arg)? },           retype: quote! { #type_name },         },         \/\/ ...       }     }   } }<\/code><\/pre>\n<p>\u041a\u043e\u0440\u0442\u0435\u0436 \u0432 Rust \u2014 \u0441\u043e\u0441\u0442\u0430\u0432\u043d\u043e\u0439 \u0442\u0438\u043f \u0434\u0430\u043d\u043d\u044b\u0445, \u043a\u043e\u0442\u043e\u0440\u044b\u0439 \u0445\u0440\u0430\u043d\u0438\u0442 \u0431\u043e\u043b\u0435\u0435 \u043e\u0434\u043d\u043e\u0433\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043e\u0434\u043d\u043e\u0432\u0440\u0435\u043c\u0435\u043d\u043d\u043e. \u0418\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u043a\u043e\u0440\u0442\u0435\u0436 \u043a\u043e\u0433\u0434\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u044f \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u0442 \u0431\u043e\u043b\u044c\u0448\u0435 \u043e\u0434\u043d\u043e\u0433\u043e \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f:<\/p>\n<pre><code class=\"rust\">pub fn get_wet_dry_mix(&amp;self) -> Result&lt;(f32, f32, f32), Error> {     unsafe {         let mut prewet = f32::default();         let mut postwet = f32::default();         let mut dry = f32::default();         match ffi::FMOD_DSP_GetWetDryMix(             self.pointer,              &amp;mut prewet,              &amp;mut postwet,              &amp;mut dry         ) {             ffi::FMOD_OK => Ok((prewet, postwet, dry)),             error => Err(err_fmod!(\"FMOD_DSP_GetWetDryMix\", error)),         }     } }<\/code><\/pre>\n<h2>\u0417\u0430\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435<\/h2>\n<p>\u0420\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0430 \u044d\u0442\u043e\u0433\u043e \u0440\u0435\u0448\u0435\u043d\u0438\u044f \u0437\u0430\u043d\u044f\u043b\u0430 \u0432 \u043e\u0431\u0449\u0435\u043c \u043e\u043a\u043e\u043b\u043e \u0434\u0432\u0443\u0445 \u0447\u0435\u043b\u043e\u0432\u0435\u043a\u043e-\u043d\u0435\u0434\u0435\u043b\u044c. \u0415\u0434\u0432\u0430 \u043b\u0438 \u0440\u0443\u0447\u043d\u043e\u0435 \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u0435 \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u0432 \u0441\u043e\u043f\u043e\u0441\u0442\u0430\u0432\u0438\u043c\u043e\u043c \u043e\u0431\u044a\u0451\u043c\u0435 \u0437\u0430\u0439\u043c\u0451\u0442 \u043c\u0435\u043d\u044c\u0448\u0435 \u0432\u0440\u0435\u043c\u0435\u043d\u0438. \u041f\u043e\u044d\u0442\u043e\u043c\u0443 \u0437\u0430\u0442\u0440\u0430\u0442\u044b \u0432 \u043b\u044e\u0431\u043e\u043c \u0441\u043b\u0443\u0447\u0430\u0435 \u043e\u043f\u0440\u0430\u0432\u0434\u0430\u043d\u044b.<\/p>\n<p>\u0423\u0434\u043e\u0431\u0441\u0442\u0432\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u043d\u0438\u044f Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u043f\u0440\u043e\u0442\u0438\u0432 FFI \u043c\u043e\u0436\u043d\u043e \u0441\u0440\u0430\u0432\u043d\u0438\u0442\u044c \u043d\u0430 \u043d\u0430\u0433\u043b\u044f\u0434\u043d\u043e\u043c \u043f\u0440\u0438\u043c\u0435\u0440\u0435:<\/p>\n<pre><code class=\"rust\">fn initialize_fmod_studio() -> Result&lt;(), Error> {     let studio = Studio::create()?;     let system = studio.get_core_system()?;     system.set_software_format(None, Some(SpeakerMode::Quad), None)?;     studio.initialize(1024, FMOD_STUDIO_INIT_NORMAL, FMOD_INIT_NORMAL, None)?; }  \/\/ Rust vs FFI  fn initialize_fmod_studio_via_ffi() -> Result&lt;(), Error> {     let mut studio = null_mut();     let result = unsafe { FMOD_Studio_System_Create(&amp;mut studio, FMOD_VERSION) };     if result != FMOD_OK {         return Err(Error(result));     }     let mut system = null_mut();     let result = unsafe { FMOD_Studio_System_GetCoreSystem(studio, &amp;mut system) };     if result != FMOD_OK {         return Err(Error(result));     }     let result = unsafe { FMOD_System_SetSoftwareFormat(system, 0, FMOD_SPEAKERMODE_QUAD, 0) };     if result != FMOD_OK {         return Err(Error(result));     }     let result = unsafe {         FMOD_Studio_System_Initialize(             studio,             1024,             FMOD_STUDIO_INIT_NORMAL,             FMOD_INIT_NORMAL,             null_mut(),         )     };     if result != FMOD_OK {         return Err(Error(result));     } }<\/code><\/pre>\n<p>\u041f\u043e\u043b\u043d\u044b\u0439 \u043a\u043e\u0434 \u0440\u0435\u0448\u0435\u043d\u0438\u044f \u043e\u0442\u043a\u0440\u044b\u0442 \u0432 \u0440\u0435\u043f\u043e\u0437\u0438\u0442\u043e\u0440\u0438\u0438 <a href=\"https:\/\/github.com\/lebedec\/libfmod-gen\" rel=\"noopener noreferrer nofollow\">libfmod-gen<\/a>.<\/p>\n<p>\u041f\u043e\u043f\u0440\u043e\u0431\u043e\u0432\u0430\u0442\u044c FMOD \u0432 Rust \u043c\u043e\u0436\u043d\u043e \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438 <a href=\"https:\/\/crates.io\/crates\/libfmod\" rel=\"noopener noreferrer nofollow\">libfmod<\/a>.<\/p>\n<\/div>\n<\/div>\n<\/div>\n<div class=\"v-portal\" style=\"display:none;\"><\/div>\n<\/div>\n<p> <!----> <!----><br \/> \u0441\u0441\u044b\u043b\u043a\u0430 \u043d\u0430 \u043e\u0440\u0438\u0433\u0438\u043d\u0430\u043b \u0441\u0442\u0430\u0442\u044c\u0438 <a href=\"https:\/\/habr.com\/ru\/post\/656525\/\"> https:\/\/habr.com\/ru\/post\/656525\/<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<div><\/div>\n<div id=\"post-content-body\">\n<div>\n<div class=\"article-formatted-body article-formatted-body_version-2\">\n<div xmlns=\"http:\/\/www.w3.org\/1999\/xhtml\">\n<p>\u041e\u0431\u0451\u0440\u0442\u043a\u0443 \u043c\u043e\u0436\u043d\u043e \u043d\u0430\u043f\u0438\u0441\u0430\u0442\u044c \u0432\u0440\u0443\u0447\u043d\u0443\u044e, \u043a\u043e\u0433\u0434\u0430 API \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0438\u0437 \u043d\u0435\u0431\u043e\u043b\u044c\u0448\u043e\u0433\u043e \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u0430 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438 \u0441\u0438\u0433\u043d\u0430\u0442\u0443\u0440\u0430 \u044d\u0442\u0438\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u043c\u0435\u043d\u044f\u0435\u0442\u0441\u044f \u043d\u0435\u0447\u0430\u0441\u0442\u043e. FMOD \u2014 \u0437\u0432\u0443\u043a\u043e\u0432\u043e\u0439 \u0434\u0432\u0438\u0436\u043e\u043a \u0441 \u0431\u043e\u043b\u044c\u0448\u0438\u043c \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e\u043c \u0444\u0443\u043d\u043a\u0446\u0438\u0439, \u0442\u043e\u0447\u043d\u043e \u043d\u0435 \u0442\u043e\u0442 \u0441\u043b\u0443\u0447\u0430\u0439:<\/p>\n<pre><code class=\"css\">Types: 19 Callbacks: 96 Structures: 57 Structure Fields: 352 Enumerations: 77 Enumeration Variants: 693 Functions: 573 Function Arguments: 1590<\/code><\/pre>\n<p>\u0421\u0442\u043e\u0438\u043c\u043e\u0441\u0442\u044c \u0440\u0443\u0447\u043d\u043e\u0439 \u0440\u0430\u0437\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u043e\u0431\u0451\u0440\u0442\u043a\u0438 \u0434\u043b\u044f \u0442\u0430\u043a\u043e\u0433\u043e API \u0431\u0443\u0434\u0435\u0442 \u0432\u044b\u0441\u043e\u043a\u043e\u0439, \u043f\u043e\u0434\u0434\u0435\u0440\u0436\u043a\u0430 \u043f\u0440\u0438 \u043a\u0430\u0436\u0434\u043e\u043c \u043e\u0431\u043d\u043e\u0432\u043b\u0435\u043d\u0438\u0438 \u043c\u0443\u0447\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0439, \u043d\u0435 \u0433\u043e\u0432\u043e\u0440\u044f \u0443\u0436\u0435 \u043e\u0431 \u043e\u0448\u0438\u0431\u043a\u0430\u0445 \u0438 \u043e\u043f\u0435\u0447\u0430\u0442\u043a\u0430\u0445, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u043f\u043e\u044f\u0432\u044f\u0442\u0441\u044f \u0432 \u043f\u0440\u043e\u0446\u0435\u0441\u0441\u0435 \u0440\u0435\u0434\u0430\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u044f.<\/p>\n<p>\u041a \u0441\u0447\u0430\u0441\u0442\u044c\u044e, FMOD \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438 \u043f\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0432\u043c\u0435\u0441\u0442\u0435 \u0441 \u0445\u043e\u0440\u043e\u0448\u043e \u043e\u0444\u043e\u0440\u043c\u043b\u0435\u043d\u043d\u044b\u043c\u0438 \u0444\u0430\u0439\u043b\u0430\u043c\u0438 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432, \u043a\u043e\u0442\u043e\u0440\u044b\u0435  \u043c\u043e\u0436\u043d\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u0434\u043b\u044f \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u043e\u0433\u043e \u0441\u043e\u0437\u0434\u0430\u043d\u0438\u044f \u043e\u0431\u0451\u0440\u0442\u043a\u0438.<\/p>\n<p>\u0412 \u044d\u043a\u043e\u0441\u0438\u0441\u0442\u0435\u043c\u0435 Rust \u043d\u0430\u0438\u0431\u043e\u043b\u0435\u0435 \u043f\u043e\u043f\u0443\u043b\u044f\u0440\u043d\u044b\u043c \u0438\u043d\u0441\u0442\u0440\u0443\u043c\u0435\u043d\u0442\u043e\u043c \u044f\u0432\u043b\u044f\u0435\u0442\u0441\u044f <a href=\"https:\/\/rust-lang.github.io\/rust-bindgen\/\" rel=\"noopener noreferrer nofollow\">bindgen<\/a> \u2014 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0430, \u043a\u043e\u0442\u043e\u0440\u0430\u044f \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u0442 Rust \u043a\u043e\u0434 \u043d\u0430 \u043e\u0441\u043d\u043e\u0432\u0435 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0445 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 C. \u041d\u043e \u0438\u043d\u0441\u0442\u0440\u0443\u043c\u0435\u043d\u0442 \u043d\u0435 \u0438\u0434\u0435\u0430\u043b\u044c\u043d\u044b\u0439, \u043f\u043e \u043d\u0435\u0441\u043a\u043e\u043b\u044c\u043a\u0438\u043c \u043f\u0440\u0438\u0447\u0438\u043d\u0430\u043c:<\/p>\n<ul>\n<li>\n<p>Bindgen \u0433\u0435\u043d\u0435\u0440\u0438\u0440\u0443\u0435\u0442 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0442\u0438\u043f\u043e\u0432 \u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f FFI, \u043d\u043e \u043d\u0430 \u043c\u0438\u043d\u0438\u043c\u0430\u043b\u044c\u043d\u043e \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u043c \u0443\u0440\u043e\u0432\u043d\u0435, \u0441 \u0441\u044b\u0440\u044b\u043c\u0438 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f\u043c\u0438 \u0438 unsafe \u0431\u043b\u043e\u043a\u0430\u043c\u0438 \u044f\u0437\u044b\u043a\u0430, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u044d\u0442\u043e \u0432 \u0438\u0434\u0438\u043e\u043c\u0430\u0442\u0438\u0447\u043d\u043e\u043c Rust \u043f\u0440\u0438\u043b\u043e\u0436\u0435\u043d\u0438\u0438 \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u0430\u0442\u0438\u0447\u043d\u043e<\/p>\n<\/li>\n<li>\n<p>\u041f\u043e\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442 \u0432\u0441\u0435 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0441\u0442\u0438 \u044f\u0437\u044b\u043a\u0430 C \u043d\u043e \u043d\u0435 \u0443\u0447\u0438\u0442\u044b\u0432\u0430\u0435\u0442 \u043a\u043e\u043d\u0442\u0435\u043a\u0441\u0442 \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u043e\u0433\u043e API, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440, \u043d\u0435 \u0440\u0430\u0437\u0431\u0435\u0440\u0451\u0442: \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438, \u043c\u0430\u043a\u0440\u043e\u0441\u044b \u0441 \u043f\u0440\u0435\u0434\u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043b\u0435\u043d\u043d\u044b\u043c\u0438 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f\u043c\u0438, \u043c\u0430\u043f\u043f\u0438\u043d\u0433 \u043e\u0448\u0438\u0431\u043e\u043a<\/p>\n<\/li>\n<li>\n<p>\u0422\u0440\u0435\u0431\u0443\u0435\u0442 \u0443\u0441\u0442\u0430\u043d\u043e\u0432\u043a\u0438 LLVM \u0441 libclang \u0432 \u043a\u043e\u043c\u043f\u043b\u0435\u043a\u0442\u0435, \u044d\u0442\u043e \u0431\u0443\u0434\u0435\u0442 \u043f\u0440\u043e\u0431\u043b\u0435\u043c\u043e\u0439 \u043d\u0430 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0445 \u043f\u043b\u0430\u0442\u0444\u043e\u0440\u043c\u0430\u0445, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440 Windows<\/p>\n<\/li>\n<\/ul>\n<p>\u0412\u043c\u0435\u0441\u0442\u043e bindgen, \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c \u0441\u043e\u0431\u0441\u0442\u0432\u0435\u043d\u043d\u043e\u0435 \u0440\u0435\u0448\u0435\u043d\u0438\u0435, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0438\u0437 \u0442\u0440\u0435\u0445 \u0448\u0430\u0433\u043e\u0432:<\/p>\n<ol>\n<li>\n<p>\u0420\u0430\u0437\u0431\u043e\u0440 API \u0438\u0437 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 \u0432 \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u0435 \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435<\/p>\n<\/li>\n<li>\n<p>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u043a\u043e\u0434\u0430 FFI \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0439<\/p>\n<\/li>\n<li>\n<p>\u0413\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u044f \u043a\u043e\u0434\u0430 Rust \u043e\u0431\u0451\u0440\u0442\u043a\u0438<\/p>\n<\/li>\n<\/ol>\n<h2>\u0420\u0430\u0437\u0431\u043e\u0440 API<\/h2>\n<p>\u0414\u043b\u044f \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0444\u0430\u0439\u043b\u043e\u0432 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 FMOD \u0431\u0443\u0434\u0435\u043c \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c \u043f\u0430\u0440\u0441\u0435\u0440 \u043e\u0431\u0449\u0435\u0433\u043e \u043d\u0430\u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f <a href=\"https:\/\/pest.rs\" rel=\"noopener noreferrer nofollow\">pest<\/a>. \u041f\u0430\u0440\u0441\u0435\u0440 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438 <a href=\"https:\/\/en.wikipedia.org\/wiki\/Parsing_expression_grammar\" rel=\"noopener noreferrer nofollow\">PEG<\/a>, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0430\u043d\u0430\u043b\u043e\u0433\u0438\u0447\u043d\u044b \u0440\u0435\u0433\u0443\u043b\u044f\u0440\u043d\u044b\u043c \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c, \u043d\u043e \u0434\u0430\u044e\u0442 \u0431\u043e\u043b\u044c\u0448\u0435 \u0432\u044b\u0440\u0430\u0437\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438, \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u0439 \u0434\u043b\u044f \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u043b\u043e\u0436\u043d\u044b\u0445 \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u043a\u043e\u043d\u0441\u0442\u0440\u0443\u043a\u0446\u0438\u0439.<\/p>\n<p>\u041f\u0440\u043e\u0441\u0442\u043e\u0439 \u043f\u0440\u0438\u043c\u0435\u0440 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438 \u0434\u043b\u044f \u0441\u043f\u0438\u0441\u043a\u0430 \u0431\u0443\u043a\u0432\u0435\u043d\u043d\u043e-\u0446\u0438\u0444\u0440\u043e\u0432\u044b\u0445 \u0438\u0434\u0435\u043d\u0442\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440\u043e\u0432:<\/p>\n<pre><code class=\"rust\">alpha = { 'a'..'z' | 'A'..'Z' } digit = { '0'..'9' } ident = { (alpha | digit)+ }<\/code><\/pre>\n<p>\u0422\u0430\u043a\u0438\u043c \u043e\u0431\u0440\u0430\u0437\u043e\u043c \u043d\u0430\u043f\u0438\u0448\u0435\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0434\u043b\u044f \u0432\u0441\u0435\u0445 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0439 \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432. \u041f\u043e\u043b\u043d\u044b\u0439 \u0440\u0430\u0437\u0431\u043e\u0440 \u044f\u0437\u044b\u043a\u0430 C \u0434\u0435\u043b\u0430\u0442\u044c \u043d\u0435 \u043d\u0443\u0436\u043d\u043e, \u0442\u043e\u043b\u044c\u043a\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u043c\u044b\u0435 \u0430\u0431\u0441\u0442\u0440\u0430\u043a\u0446\u0438\u0438 \u0438 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u043d\u044b\u0435 \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u044b FMOD. \u042d\u0442\u043e \u0441\u043e\u043a\u0440\u0430\u0449\u0430\u0435\u0442 \u0432\u0440\u0435\u043c\u044f \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u0438.<\/p>\n<pre><code class=\"rust\">declaration = _{ Function | Directive | ExternLinkage } API = { SOI ~ declaration* ~ EOI  }<\/code><\/pre>\n<p>\u0422\u0438\u043f\u0430\u0436 <code>Parser<\/code> \u2014 \u044f\u0434\u0440\u043e pest, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u043f\u0440\u0435\u0434\u043e\u0441\u0442\u0430\u0432\u043b\u044f\u0435\u0442 \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u0434\u043b\u044f \u0441\u0438\u043d\u0442\u0430\u043a\u0441\u0438\u0447\u0435\u0441\u043a\u043e\u0433\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430. \u0420\u0435\u0430\u043b\u0438\u0437\u043e\u0432\u044b\u0432\u0430\u0442\u044c \u0432\u0440\u0443\u0447\u043d\u0443\u044e \u0438\u043d\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043d\u0435 \u043d\u0443\u0436\u043d\u043e, \u043c\u0430\u043a\u0440\u043e\u0441 \u0438\u0437 \u0431\u0438\u0431\u043b\u0438\u043e\u0442\u0435\u043a\u0438 <code>pest_derive<\/code> \u043c\u043e\u0436\u0435\u0442 \u0430\u0432\u0442\u043e\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u0438 \u0441\u0433\u0435\u043d\u0435\u0440\u0438\u0440\u043e\u0432\u0430\u0442\u044c \u043a\u043e\u0434 \u0438\u0437 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0438:<\/p>\n<pre><code class=\"rust\">#[derive(Parser)] #[grammar = \".\/grammars\/fmod.pest\"] struct FmodParser;<\/code><\/pre>\n<p>\u041f\u043e\u043b\u0443\u0447\u0435\u043d\u0438\u0435 \u0434\u0430\u043d\u043d\u044b\u0445 \u0434\u043b\u044f \u043e\u0431\u0440\u0430\u0431\u043e\u0442\u043a\u0438 \u0441\u0432\u043e\u0434\u0438\u0442\u0441\u044f \u043a \u043f\u0435\u0440\u0435\u0431\u043e\u0440\u0443 \u0438 \u0438\u043d\u0442\u0435\u0440\u043f\u0440\u0435\u0442\u0430\u0446\u0438\u0438 \u043f\u0440\u0430\u0432\u0438\u043b \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u044b\u0445 \u0432 \u044d\u0442\u0438\u0445 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a\u0430\u0445:<\/p>\n<pre><code class=\"rust\">pub struct Header {     pub functions: Vec&lt;Function>, }  pub fn parse(source: &amp;str) -> Result&lt;Header, Error> {   let mut header = Header::default();      let declarations = FmodParser::parse(Rule::API, source)?         .next()         .ok_or(Error::FileMalformed)?;      for declaration in declarations.into_inner() {         match declaration.as_rule() {             Rule::Function => header.add_function(declaration),             Rule::Directive => ...,             Rule::ExternLinkage => ...,         }     }      Ok(header) }<\/code><\/pre>\n<h3>\u041d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u044b\u0435 \u0442\u0438\u043f\u044b<\/h3>\n<p>\u0412\u0441\u0435 \u043e\u0431\u044a\u0435\u043a\u0442\u044b FMOD \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442\u0441\u044f \u0432 \u0432\u0438\u0434\u0435 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044f \u043d\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0443. \u042d\u0442\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430 \u043d\u0430\u0437\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u201c\u043d\u0435\u043f\u0440\u043e\u0437\u0440\u0430\u0447\u043d\u043e\u0439\u201d \u043f\u043e\u0442\u043e\u043c\u0443 \u0447\u0442\u043e \u0441\u043a\u0440\u044b\u0432\u0430\u0435\u0442 \u0434\u0435\u0442\u0430\u043b\u0438 \u0440\u0435\u0430\u043b\u0438\u0437\u0430\u0446\u0438\u0438, \u0431\u0443\u0434\u044c \u0442\u043e \u0434\u0435\u0441\u043a\u0440\u0438\u043f\u0442\u043e\u0440 \u0438\u043b\u0438 \u043f\u0440\u044f\u043c\u043e\u0439 \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044c \u043d\u0430 \u043e\u0431\u044a\u0435\u043a\u0442. \u0414\u043b\u044f \u043e\u0431\u043e\u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0438\u043c\u0435\u043d\u0438 \u0442\u0438\u043f\u0430 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f <code>typedef<\/code>, \u043d\u0430\u043f\u0440\u0438\u043c\u0435\u0440:<\/p>\n<pre><code class=\"cpp\">typedef struct FMOD_SYSTEM         FMOD_SYSTEM; typedef struct FMOD_SOUND          FMOD_SOUND; typedef struct FMOD_CHANNEL        FMOD_CHANNEL;<\/code><\/pre>\n<p>\u0413\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u0447\u0435\u0441\u043a\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430 \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u043e\u0441\u0442\u043e\u044f\u0442 \u0438\u0437 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0439. \u042d\u0442\u0438 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u044f\u044e\u0442 \u0441\u043e\u0431\u043e\u0439 \u0444\u043e\u0440\u043c\u0430\u043b\u044c\u043d\u043e\u0435 \u043e\u043f\u0438\u0441\u0430\u043d\u0438\u0435 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u0438\u044f \u0441\u0442\u0440\u043e\u043a\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044e. \u0412\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f \u043c\u043e\u0436\u043d\u043e \u043a\u043e\u043c\u043f\u043e\u043d\u043e\u0432\u0430\u0442\u044c \u0438\u0437 \u0434\u0440\u0443\u0433\u0438\u0445 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0439, \u0432\u043a\u043b\u0430\u0434\u044b\u0432\u0430\u0442\u044c \u0434\u0440\u0443\u0433 \u0432 \u0434\u0440\u0443\u0433\u0430.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u0432\u044b\u0431\u043e\u0440\u0430 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>|<\/code>. \u041f\u0430\u0440\u0441\u0435\u0440 \u0432\u044b\u0431\u0438\u0440\u0430\u0435\u0442 \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u043c \u043f\u043e\u0440\u044f\u0434\u043a\u0435 \u043f\u0435\u0440\u0432\u043e\u0435 \u0443\u0441\u043f\u0435\u0448\u043d\u043e\u0435 \u0441\u043e\u043f\u043e\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u0435.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0437\u0430\u043f\u0438\u0441\u044b\u0432\u0430\u0435\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>~<\/code>. \u041e\u043d \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0441\u0442\u0440\u043e\u043a\u0430 \u0434\u043e\u043b\u0436\u043d\u0430 \u0441\u043e\u043e\u0442\u0432\u0435\u0442\u0441\u0442\u0432\u043e\u0432\u0430\u0442\u044c \u0432\u0441\u0435\u043c \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c \u0432 \u0443\u043a\u0430\u0437\u0430\u043d\u043d\u043e\u043c \u043f\u043e\u0440\u044f\u0434\u043a\u0435.<\/p>\n<p>\u0420\u0443\u0447\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u043f\u0440\u0430\u0432\u0438\u043b \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u043f\u0440\u043e\u0431\u0435\u043b\u043e\u0432 \u0438 \u043e\u0442\u0441\u0442\u0443\u043f\u043e\u0432 \u0437\u0430\u0442\u0440\u0443\u0434\u043d\u044f\u0435\u0442 \u0447\u0442\u0435\u043d\u0438\u0435 \u0438 \u0440\u0435\u0434\u0430\u043a\u0442\u0438\u0440\u043e\u0432\u0430\u043d\u0438\u0435 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a. \u0415\u0441\u043b\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0441\u043f\u0435\u0446\u0438\u0430\u043b\u044c\u043d\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e <code>WHITESPACE<\/code>, \u043e\u043d\u043e \u0431\u0443\u0434\u0435\u0442 \u043e\u0431\u0440\u0430\u0431\u0430\u0442\u044b\u0432\u0430\u0442\u044c\u0441\u044f \u043d\u0435\u044f\u0432\u043d\u043e \u043c\u0435\u0436\u0434\u0443 \u0434\u0440\u0443\u0433\u0438\u043c\u0438 \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u044f\u043c\u0438.<\/p>\n<p>\u0418\u043c\u044f \u0442\u0438\u043f\u0430 \u0432\u043a\u043b\u044e\u0447\u0430\u0435\u0442 \u0446\u0438\u0444\u0440\u044b, \u0430\u043d\u0433\u043b\u0438\u0439\u0441\u043a\u0438\u0435 \u0431\u0443\u043a\u0432\u044b \u0438 \u0441\u0438\u043c\u0432\u043e\u043b\u044b \u043f\u043e\u0434\u0447\u0435\u0440\u043a\u0438\u0432\u0430\u043d\u0438\u044f. \u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>+<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u0447\u0442\u043e \u0438\u043c\u044f \u0441\u043e\u0441\u0442\u043e\u0438\u0442 \u0445\u043e\u0442\u044f \u0431\u044b \u0438\u0437 \u043e\u0434\u043d\u043e\u0433\u043e \u0441\u0438\u043c\u0432\u043e\u043b\u0430. \u041c\u0435\u0436\u0434\u0443 \u044d\u0442\u0438\u043c\u0438 \u0441\u0438\u043c\u0432\u043e\u043b\u0430\u043c\u0438 \u043d\u0435 \u0434\u043e\u043b\u0436\u043d\u043e \u0431\u044b\u0442\u044c \u043f\u0440\u043e\u0431\u0435\u043b\u043e\u0432, \u043f\u043e\u044d\u0442\u043e\u043c\u0443 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u043e\u0442\u043c\u0435\u0447\u0435\u043d\u043e \u043a\u0430\u043a \u0430\u0442\u043e\u043c\u0430\u0440\u043d\u043e\u0435 \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0437\u043d\u0430\u043a\u0430 <code>@<\/code>.<\/p>\n<pre><code class=\"rust\">WHITESPACE = _{ \" \" | \"\\\\t\" }  name = @{ (\"_\" | ASCII_ALPHANUMERIC)+ }  OpaqueType = { \"typedef\" ~ \"struct\" ~ name ~ name ~ \";\"}<\/code><\/pre>\n<h3>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f<\/h3>\n<p>\u041f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u0435 \u2014 \u044d\u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c\u044b\u0439 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0442\u0438\u043f, \u0441\u043e\u0441\u0442\u043e\u044f\u0449\u0438\u0439 \u0438\u0437 \u043d\u0430\u0431\u043e\u0440\u0430 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u0446\u0435\u043b\u043e\u0447\u0438\u0441\u043b\u0435\u043d\u043d\u044b\u0445 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442. \u041f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 C \u044d\u0442\u0438 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0435 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u044b \u043d\u0430\u0437\u044b\u0432\u0430\u044e\u0442\u0441\u044f &#171;\u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f\u043c\u0438\u201d. \u0412\u043e\u0437\u043c\u043e\u0436\u043d\u043e \u044f\u0432\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u044f, \u043a\u0430\u043a \u043f\u043e\u043a\u0430\u0437\u0430\u043d\u043e \u0437\u0434\u0435\u0441\u044c:<\/p>\n<pre><code class=\"cpp\">typedef enum FMOD_PORT_TYPE {     FMOD_PORT_TYPE_MUSIC,     FMOD_PORT_TYPE_VOICE,     FMOD_PORT_TYPE_FORCEINT = 65536 } FMOD_PORT_TYPE;<\/code><\/pre>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>*<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u0432\u0441\u0442\u0440\u0435\u0447\u0430\u0435\u0442\u0441\u044f \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u043e\u0435 \u043a\u043e\u043b\u0438\u0447\u0435\u0441\u0442\u0432\u043e \u0440\u0430\u0437. \u0421\u043f\u0438\u0441\u043e\u043a \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0438\u0442\u0435\u043b\u0435\u0439 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u044b\u043c \u043f\u0440\u0430\u0432\u0438\u043b\u043e\u043c <code>enumerators<\/code>, \u044d\u0442\u043e \u043f\u0440\u0438\u0433\u043e\u0434\u0438\u0442\u0441\u044f \u0434\u0430\u043b\u044c\u0448\u0435 \u043d\u0430 \u044d\u0442\u0430\u043f\u0435 \u043f\u0440\u043e\u043c\u0435\u0436\u0443\u0442\u043e\u0447\u043d\u043e\u0433\u043e \u043f\u0440\u0435\u0434\u0441\u0442\u0430\u0432\u043b\u0435\u043d\u0438\u044f \u0440\u0430\u0437\u043e\u0431\u0440\u0430\u043d\u043d\u044b\u0445 \u0434\u0430\u043d\u043d\u044b\u0445.<\/p>\n<p>\u041e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 \u043f\u043e\u0432\u0442\u043e\u0440\u0435\u043d\u0438\u044f <code>?<\/code> \u0443\u043a\u0430\u0437\u044b\u0432\u0430\u0435\u0442 \u043d\u0430 \u0442\u043e, \u0447\u0442\u043e \u0432\u044b\u0440\u0430\u0436\u0435\u043d\u0438\u0435 \u043d\u0435\u043e\u0431\u044f\u0437\u0430\u0442\u0435\u043b\u044c\u043d\u043e \u2014 \u043c\u043e\u0436\u0435\u0442 \u0432\u0441\u0442\u0440\u0435\u0447\u0430\u0442\u044c\u0441\u044f \u043d\u043e\u043b\u044c \u0438\u043b\u0438 \u043e\u0434\u0438\u043d \u0440\u0430\u0437.<\/p>\n<pre><code class=\"rust\">Enumerator = { \",\"? ~ name ~ (\"=\" ~ value)? } enumerators = { Enumerator* } Enumeration = {  \"typedef\" ~ \"enum\" ~ name ~ \"{\" ~ enumerators ~ \"}\" ~  name ~ \";\"  }<\/code><\/pre>\n<h3>\u0411\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438<\/h3>\n<p>\u0412 FMOD \u0447\u0430\u0441\u0442\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0442\u0441\u044f \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438, \u0432\u043c\u0435\u0441\u0442\u043e \u0434\u043b\u0438\u043d\u043d\u043e\u0439 \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u043b\u043e\u0433\u0438\u0447\u0435\u0441\u043a\u0438\u0445 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439 \u0432 \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u0430\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u0438\u043b\u0438 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440. \u0424\u043b\u0430\u0433\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e <code>typedef<\/code> \u043a\u0430\u043a \u0441\u0438\u043d\u043e\u043d\u0438\u043c \u0431\u0430\u0437\u043e\u0432\u043e\u0433\u043e \u0442\u0438\u043f\u0430, \u044d\u0442\u043e \u0434\u0430\u0435\u0442 \u043d\u0435\u043a\u043e\u0442\u043e\u0440\u0443\u044e \u0431\u0435\u0437\u043e\u043f\u0430\u0441\u043d\u043e\u0441\u0442\u044c \u0442\u0438\u043f\u043e\u0432. \u0421 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0434\u0438\u0440\u0435\u043a\u0442\u0438\u0432\u044b <code>#define<\/code> \u0441\u043e\u0437\u0434\u0430\u044e\u0442\u0441\u044f \u043c\u0430\u043a\u0440\u043e\u0441\u044b, \u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0438\u043c\u0435\u043d\u0443\u044e\u0442 \u043a\u043e\u043d\u043a\u0440\u0435\u0442\u043d\u044b\u0435 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u0444\u043b\u0430\u0433\u043e\u0432:<\/p>\n<pre><code class=\"cpp\">typedef unsigned int FMOD_CHANNELMASK; #define FMOD_CHANNELMASK_FRONT_LEFT     0x00000001 #define FMOD_CHANNELMASK_FRONT_RIGHT    0x00000002 #define FMOD_CHANNELMASK_MONO           (FMOD_CHANNELMASK_FRONT_LEFT) #define FMOD_CHANNELMASK_STEREO         (FMOD_CHANNELMASK_FRONT_LEFT | FMOD_CHANNELMASK_FRONT_RIGHT)<\/code><\/pre>\n<p>\u0415\u0441\u043b\u0438 \u043f\u043e\u0434\u0445\u043e\u0434\u0438\u0442\u044c \u043a \u0440\u0430\u0437\u0431\u043e\u0440\u0443 \u0442\u0430\u043a\u043e\u0433\u043e \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u043f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 \u044f\u0437\u044b\u043a\u0430 \u0421, \u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0438\u0442\u044c \u0431\u0438\u0442\u043e\u0432\u044b\u0435 \u0444\u043b\u0430\u0433\u0438 \u043d\u0435\u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e, \u043f\u043e\u043b\u0443\u0447\u0430\u0435\u0442\u0441\u044f \u043d\u0430\u0431\u043e\u0440 \u043d\u0435 \u0441\u0432\u044f\u0437\u0430\u043d\u043d\u044b\u0445 \u043c\u0435\u0436\u0434\u0443 \u0441\u043e\u0431\u043e\u0439 \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u0439. Pest \u043f\u043e\u0437\u0432\u043e\u043b\u044f\u0435\u0442 \u043d\u0430\u043f\u0438\u0441\u0430\u0442\u044c \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430, \u043a\u043e\u0442\u043e\u0440\u043e\u0435 \u0431\u0443\u0434\u0435\u0442 \u0443\u0441\u0442\u0430\u043d\u0430\u0432\u043b\u0438\u0432\u0430\u0442\u044c \u043a\u043e\u043d\u0442\u0435\u043a\u0441\u0442 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u044f \u0431\u0438\u0442\u043e\u0432\u044b\u0445 \u0444\u043b\u0430\u0433\u043e\u0432.<\/p>\n<p>\u041c\u0430\u043a\u0440\u043e\u0441 \u043c\u043e\u0436\u0435\u0442 \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u0442\u044c \u043d\u0435 \u0442\u043e\u043b\u044c\u043a\u043e \u043b\u0438\u0442\u0435\u0440\u0430\u043b\u044b, \u043d\u043e \u0438 \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u044b\u0435 \u0432\u044b\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f. \u0427\u0442\u043e\u0431\u044b \u043d\u0435 \u0440\u0430\u0437\u0431\u0438\u0440\u0430\u0442\u044c \u0432\u0441\u0435 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u044b\u0435 \u0441\u0446\u0435\u043d\u0430\u0440\u0438\u0438, \u0432\u044b\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u043e\u043f\u0438\u0441\u044b\u0432\u0430\u044e\u0442\u0441\u044f \u043a\u0430\u043a \u043f\u043e\u0441\u043b\u0435\u0434\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u044c \u043b\u044e\u0431\u044b\u0445 \u0441\u0438\u043c\u0432\u043e\u043b\u043e\u0432 <code>ANY<\/code> \u0432 \u0441\u043a\u043e\u0431\u043a\u0430\u0445. \u0423\u043f\u0440\u0435\u0436\u0434\u0430\u044e\u0449\u0438\u0439 \u043e\u043f\u0435\u0440\u0430\u0442\u043e\u0440 <code>!<\/code> \u043e\u0433\u0440\u0430\u043d\u0438\u0447\u0438\u0432\u0430\u0435\u0442 \u0432\u043a\u043b\u044e\u0447\u0435\u043d\u0438\u0435 \u0437\u0430\u043a\u0440\u044b\u0432\u0430\u044e\u0449\u0435\u0439 \u0441\u043a\u043e\u0431\u043a\u0438.<\/p>\n<pre><code class=\"rust\">Calculation = { \"(\" ~ (!\")\" ~ ANY)* ~ \")\" } Literal = { (\"-\" | \"_\" | ASCII_ALPHANUMERIC)+ } value = @{ Calculation | Literal } Flag = { \"#define\" ~ name ~ value } flags = { Flag+ } flags_type = { FundamentalType } Flags = { \"typedef\" ~ flags_type ~ name ~ \";\" ~ flags  }<\/code><\/pre>\n<h3>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b<\/h3>\n<p>\u0421\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u0430 \u2014 \u044d\u0442\u043e \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u043c\u044b\u0439 \u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u0435\u043c \u0441\u043e\u0441\u0442\u0430\u0432\u043d\u043e\u0439 \u0442\u0438\u043f, \u0438\u043d\u043a\u0430\u043f\u0441\u0443\u043b\u0438\u0440\u0443\u044e\u0449\u0438\u0439\u00a0\u043d\u0430\u0431\u043e\u0440\u00a0\u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u043d\u044b\u0445 \u043f\u043e\u043b\u0435\u0439\u00a0\u0440\u0430\u0437\u043b\u0438\u0447\u043d\u044b\u0445 \u0442\u0438\u043f\u043e\u0432. \u041d\u0435\u043a\u043e\u0442\u043e\u0440\u044b\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u0438\u043c\u0435\u044e\u0442 \u0441\u043b\u043e\u0436\u043d\u043e\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u0435. \u0412 \u043d\u0438\u0445 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u044e\u0442\u0441\u044f \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u0438 \u043c\u0430\u0441\u0441\u0438\u0432\u044b:<\/p>\n<pre><code class=\"cpp\">typedef struct FMOD_DSP_PARAMETER_DESC  {     FMOD_DSP_PARAMETER_TYPE type;     char                    name[16];     char                    label[16];     const char             *description;      union     {         FMOD_DSP_PARAMETER_DESC_FLOAT   floatdesc;         FMOD_DSP_PARAMETER_DESC_INT     intdesc;         FMOD_DSP_PARAMETER_DESC_BOOL    booldesc;         FMOD_DSP_PARAMETER_DESC_DATA    datadesc;     }; } FMOD_DSP_PARAMETER_DESC;<\/code><\/pre>\n<p>\u0422\u0438\u043f\u044b \u043f\u043e\u043b\u0435\u0439:<\/p>\n<ul>\n<li>\n<p>\u0424\u0443\u043d\u0434\u0430\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u0435 \u0442\u0438\u043f\u044b. \u041e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u044b \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u043e\u043c \u044f\u0437\u044b\u043a\u0430, \u0432\u0441\u0442\u0440\u043e\u0435\u043d\u044b \u0432 \u043a\u043e\u043c\u043f\u0438\u043b\u044f\u0442\u043e\u0440. \u041d\u0435\u0442 \u043d\u0435\u043e\u0431\u0445\u043e\u0434\u0438\u043c\u043e\u0441\u0442\u0438 \u0440\u0430\u0437\u0431\u0438\u0440\u0430\u0442\u044c \u0432\u0441\u0435 \u0444\u0443\u043d\u0434\u0430\u043c\u0435\u043d\u0442\u0430\u043b\u044c\u043d\u044b\u0435 \u0442\u0438\u043f\u044b, \u0434\u043e\u0441\u0442\u0430\u0442\u043e\u0447\u043d\u043e \u0442\u0435\u0445 \u0447\u0442\u043e \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442 FMOD<\/p>\n<\/li>\n<li>\n<p>\u041f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u0435\u043b\u044c\u0441\u043a\u0438\u0435 \u0442\u0438\u043f\u044b. \u0421\u0438\u043d\u043e\u043d\u0438\u043c\u044b, \u043f\u0435\u0440\u0435\u0447\u0438\u0441\u043b\u0435\u043d\u0438\u044f \u0438 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u043d\u044b\u0435 \u043f\u043e\u0434 \u0443\u043d\u0438\u043a\u0430\u043b\u044c\u043d\u044b\u043c\u0438 \u0438\u043c\u0435\u043d\u0430\u043c\u0438 \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432 FMOD<\/p>\n<\/li>\n<\/ul>\n<pre><code class=\"rust\">FundamentalType = {     \"char\" | \"unsigned char\" | \"signed char\" |     \"int\" | \"unsigned int\" |     \"short\" | \"unsigned short\" |     \"long long\" | \"long\" | \"unsigned long long\" | \"unsigned long\" |     \"void\" |     \"float\" } UserType = @{ name } field_type = { FundamentalType | UserType }<\/code><\/pre>\n<p>\u041f\u043e\u043b\u044f \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u044f\u044e\u0442\u0441\u044f \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u0441\u0438\u043c\u0432\u043e\u043b\u0430 <code>*<\/code>. \u041c\u043e\u0434\u0438\u0444\u0438\u043a\u0430\u0442\u043e\u0440 \u0442\u0438\u043f\u0430 <code>const<\/code> \u043c\u043e\u0436\u0435\u0442 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u043e\u0432\u0430\u0442\u044c\u0441\u044f \u0434\u043b\u044f \u0437\u0430\u0449\u0438\u0442\u044b \u0437\u043d\u0430\u0447\u0435\u043d\u0438\u044f \u043f\u043e\u043b\u044f \u043e\u0442 \u0432\u043e\u0437\u043c\u043e\u0436\u043d\u043e\u0433\u043e \u0438\u0437\u043c\u0435\u043d\u0435\u043d\u0438\u044f \u043f\u043e \u0443\u043a\u0430\u0437\u0430\u0442\u0435\u043b\u044e.<\/p>\n<pre><code class=\"rust\">as_const = { \"const\" } NormalPointer = { \"*\" } DoublePointer = { \"**\" } pointer = { DoublePointer | NormalPointer }<\/code><\/pre>\n<p>\u041e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u044f\u0435\u0442 \u043d\u0430\u0431\u043e\u0440 \u043f\u043e\u043b\u0435\u0439 \u0438 \u0445\u0440\u0430\u043d\u0438\u0442 \u0442\u043e\u043b\u044c\u043a\u043e \u043e\u0434\u043d\u043e \u0438\u0437 \u043d\u0438\u0445. \u041f\u043e \u0441\u0442\u0430\u043d\u0434\u0430\u0440\u0442\u0443 C, \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u043c\u043e\u0436\u043d\u043e \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u0442\u044c \u0442\u0435\u0433\u043e\u043c, \u043d\u043e \u0432 FMOD \u044d\u0442\u043e \u043d\u0435 \u0438\u0441\u043f\u043e\u043b\u044c\u0437\u0443\u0435\u0442\u0441\u044f. \u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u043e\u0431\u044a\u0435\u0434\u0438\u043d\u0435\u043d\u0438\u044f \u043f\u043e\u0434\u0447\u0438\u043d\u044f\u044e\u0442\u0441\u044f \u0442\u0435\u043c \u0436\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u0430\u043c, \u0447\u0442\u043e \u0438 \u043e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440\u044b:<\/p>\n<pre><code class=\"rust\">union = { \"union\" ~ \"{\" ~ fields ~ \"}\" ~ \";\" }<\/code><\/pre>\n<p>\u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u043c\u0430\u0441\u0441\u0438\u0432\u0430 \u044d\u0442\u043e \u0447\u0430\u0441\u0442\u044c \u0438\u043c\u0435\u043d\u043e\u0432\u0430\u043d\u0438\u044f \u043f\u043e\u043b\u044f, \u0430 \u043d\u0435 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0442\u0438\u043f\u0430. \u0427\u0438\u0441\u043b\u043e \u044d\u043b\u0435\u043c\u0435\u043d\u0442\u043e\u0432 \u043c\u0430\u0441\u0441\u0438\u0432\u0430 \u043c\u043e\u0436\u0435\u0442 \u0431\u044b\u0442\u044c \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u043e \u0447\u0435\u0440\u0435\u0437 \u043a\u043e\u043d\u0441\u0442\u0430\u043d\u0442\u0443:<\/p>\n<pre><code class=\"rust\">as_array = { \"[\" ~ (\"_\" | ASCII_ALPHANUMERIC)+ ~ \"]\" }<\/code><\/pre>\n<p>\u0411\u043b\u0430\u0433\u043e\u0434\u0430\u0440\u044f \u0432\u044b\u0440\u0430\u0437\u0438\u0442\u0435\u043b\u044c\u043d\u043e\u0441\u0442\u0438 \u0433\u0440\u0430\u043c\u043c\u0430\u0442\u0438\u043a \u043f\u043e\u043b\u043d\u043e\u0435 \u043f\u0440\u0430\u0432\u0438\u043b\u043e \u0440\u0430\u0437\u0431\u043e\u0440\u0430 \u0441\u0442\u0440\u0443\u043a\u0442\u0443\u0440 \u0443\u043c\u0435\u0449\u0430\u0435\u0442\u0441\u044f \u0431\u0443\u043a\u0432\u0430\u043b\u044c\u043d\u043e \u0432 \u043f\u0430\u0440\u0443 \u0434\u0435\u0441\u044f\u0442\u043a\u043e\u0432 \u0441\u0442\u0440\u043e\u043a:<\/p>\n<pre><code class=\"rust\">as_const = { \"const\" } as_array = { \"[\" ~ (\"_\" | ASCII_ALPHANUMERIC)+ ~ \"]\" } NormalPointer = { \"*\" } DoublePointer = { \"**\" } pointer = { DoublePointer | NormalPointer }  field_type = { FundamentalType | UserType } Field = { as_const? ~ field_type ~ pointer? ~ name ~ as_array? ~ \";\" } fields = { Field* }  union = { \"union\" ~ \"{\" ~ fields ~ \"}\" ~ \";\" }  Structure = {  \"typedef\"? ~ \"struct\" ~ name ~ \"{\" ~  fields ~  union? ~  \"}\" ~ name? ~ \";\"  }<\/code><\/pre>\n<h2>\u0424\u0443\u043d\u043a\u0446\u0438\u0438<\/h2>\n<p>\u0424\u0443\u043d\u043a\u0446\u0438\u044f \u2014 \u043a\u043b\u044e\u0447\u0435\u0432\u043e\u0439 \u043f\u0440\u043e\u0433\u0440\u0430\u043c\u043c\u043d\u044b\u0439 \u044d\u043b\u0435\u043c\u0435\u043d\u0442, \u0441 \u043f\u043e\u043c\u043e\u0449\u044c\u044e \u043a\u043e\u0442\u043e\u0440\u043e\u0433\u043e \u0440\u0435\u0448\u0430\u044e\u0442\u0441\u044f \u0437\u0430\u0434\u0430\u0447\u0438 FMOD. \u041e\u0431\u044a\u044f\u0432\u043b\u0435\u043d\u0438\u0435 \u0444\u0443\u043d\u043a\u0446\u0438\u0439 \u043e\u0442\u0434\u0435\u043b\u044c\u043d\u043e \u043e\u0442 \u043e\u043f\u0440\u0435\u0434\u0435\u043b\u0435\u043d\u0438\u044f \u0441\u043e\u0434\u0435\u0440\u0436\u0438\u0442\u0441\u044f \u0432 \u0444\u0430\u0439\u043b\u0430\u0445 \u0437\u0430\u0433\u043e\u043b\u043e\u0432\u043a\u043e\u0432, \u0432\u043a\u043b\u044e\u0447\u0430\u0435\u0442 \u0432 \u0441\u0435\u0431\u044f \u0438\u043c\u044f, \u0430\u0440\u0433\u0443\u043c\u0435\u043d\u0442\u044b, \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0439 \u0442\u0438\u043f \u0438 \u0430\u0442\u0440\u0438\u0431\u0443\u0442\u044b \u0444\u0443\u043d\u043a\u0446\u0438\u0438.<\/p>\n<pre><code class=\"cpp\">FMOD_RESULT F_API FMOD_System_Create (FMOD_SYSTEM **system, unsigned int headerversion);<\/code><\/pre>\n<p>\u0422\u043e\u043b\u044c\u043a\u043e \u0443 \u0433\u043b\u043e\u0431\u0430\u043b\u044c\u043d\u044b\u0445 \u0444\u0443\u043d\u043a\u0446\u0438\u0438 FMOD \u043f\u0440\u043e\u0438\u0437\u0432\u043e\u043b\u044c\u043d\u044b\u0439 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u0435\u043c\u044b\u0439 \u0442\u0438\u043f. \u0424\u0443\u043d\u043a\u0446\u0438\u0438 \u043e\u0431\u044a\u0435\u043a\u0442\u043e\u0432 \u0432\u0441\u0435\u0433\u0434\u0430 \u0432\u043e\u0437\u0432\u0440\u0430\u0449\u0430\u044e\u0442 \u0441\u0442\u0430\u0442\u0443\u0441 \u0432\u044b\u043f\u043e\u043b\u043d\u0435\u043d\u0438\u044f <code>FMOD_RESULT<\/code>, \u0430<\/p>\n<\/div>\n<\/div>\n<\/div>\n<\/div>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[],"tags":[],"class_list":["post-330858","post","type-post","status-publish","format-standard","hentry"],"_links":{"self":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/330858","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=330858"}],"version-history":[{"count":0,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=\/wp\/v2\/posts\/330858\/revisions"}],"wp:attachment":[{"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=330858"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=330858"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/savepearlharbor.com\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=330858"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}