| {{/* |
| * Copyright (C) 2015 The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */}} |
| |
| {{/* ---- Includes ---- */}} |
| {{Include "api_classnames.tmpl"}} |
| {{Include "cpp_common.tmpl" }} |
| |
| {{/* ---- Overrides ---- */}} |
| {{Global "C++.EnumTypeOverride" "uint32_t"}} |
| {{Global "C++.ExternPrefix" "mState." }} |
| |
| {{$filename := print (Global "API") "_spy.h" }} |
| {{Global "SpyName" (print (Title (Global "API")) "Spy")}} |
| {{$ | Macro "Spy" | Format (Global "clang-format") | Write $filename}} |
| |
| {{define "Spy"}} |
| {{AssertType $ "API"}} |
| {{Macro "C++.AOSP.Copyright"}} |
| {{$spyname := Global "SpyName"}} |
| {{$guard := print "GAPII_" (Upper (Global "API")) "_SPY_H"}} |
| ¶ |
| #ifndef {{$guard}} |
| #define {{$guard}} |
| ¶ |
| #include "{{Global "API"}}_imports.h" |
| #include "{{Global "API"}}_state.h" |
| #include "{{Global "API"}}_types.h" |
| ¶ |
| #include <gapic/encoder.h> |
| #include <gapic/log.h> |
| ¶ |
| #include <memory> |
| #include <string> |
| #include <unordered_set> |
| ¶ |
| #include <stdint.h> |
| ¶ |
| namespace gapii {« |
| ¶ |
| class {{$spyname}} { |
| «public:» |
| inline {{$spyname}}(); |
| ¶ |
| inline void init(std::shared_ptr<gapic::Encoder> encoder); |
| ¶ |
| {{range $f := AllCommands $}} |
| {{Macro "MethodDefinitions" $f}} |
| {{end}} |
| ¶ |
| «protected:» |
| {{Macro "ApiClassnames.Imports"}} mImports; |
| {{Macro "ApiClassnames.State" }} mState; |
| ¶ |
| «private:» |
| enum order { |
| PRE_OBSERVE, |
| POST_OBSERVE, |
| }; |
| ¶ |
| inline void observe(const void* base, uint64_t offset, uint64_t size); |
| ¶ |
| std::unordered_set<gapic::Id> mObserved; |
| std::shared_ptr<gapic::Encoder> mEncoder; |
| }; |
| ¶ |
| inline {{$spyname}}::{{$spyname}}() |
| : mState(std::bind(&GlesSpy::observe, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3)) {} |
| ¶ |
| // Inline methods |
| inline void {{$spyname}}::init(std::shared_ptr<gapic::Encoder> encoder) { |
| mEncoder = encoder; |
| mImports.Resolve(); |
| } |
| ¶ |
| inline void {{$spyname}}::observe(const void* base, uint64_t offset, uint64_t size) { |
| const void* ptr = reinterpret_cast<const uint8_t*>(base) + offset; |
| gapic::Id id = gapic::Id::Hash(ptr, size); |
| if (mObserved.count(id) == 0) { |
| mEncoder->Uint16(0xfffd); // Type ID -- TODO: mEncoder->Id(RESOURCE_ID); |
| mEncoder->Id(id); |
| mEncoder->Data(ptr, static_cast<int32_t>(size)); |
| mObserved.emplace(id); |
| } |
| mEncoder->Uint16(0xfffe); // Type ID -- TODO: mEncoder->Id(OBSERVATION_ID); |
| mEncoder->Uint64(reinterpret_cast<uint64_t>(ptr)); |
| mEncoder->Uint64(size); |
| mEncoder->Id(id); |
| } |
| ¶ |
| {{range $i, $f := AllCommands $}} |
| {{Global "HACK_FUNCTION_INDEX_HACK" $i}} |
| {{Macro "MethodImplementation" $f}}¶ |
| {{end}} |
| ¶ |
| »} // namespace gapii |
| ¶ |
| #endif // {{$guard}} |
| ¶ |
| {{end}} |
| |
| |
| {{/* |
| ------------------------------------------------------------------------------- |
| Emits the static variable name holding the ID of the given function. |
| ------------------------------------------------------------------------------- |
| */}} |
| {{define "ID"}} |
| {{AssertType $ "Function"}} |
| |
| {{Macro "CmdName" $ | SplitPascalCase | Upper | JoinWith "_"}}_ID |
| {{end}} |
| |
| |
| {{/* |
| ------------------------------------------------------------------------------- |
| Emits a single C++ method definition for the given atom. |
| ------------------------------------------------------------------------------- |
| */}} |
| {{define "MethodDefinitions"}} |
| {{AssertType $ "Function"}} |
| |
| inline {{Macro "C++.ReturnType" $}} {{Macro "CmdName" $}}({{Macro "C++.CallParameters" $}}); |
| {{end}} |
| |
| |
| {{/* |
| ------------------------------------------------------------------------------- |
| Emits the inline method body for the given atom. |
| ------------------------------------------------------------------------------- |
| */}} |
| {{define "MethodImplementation"}} |
| {{AssertType $ "Function"}} |
| |
| {{$name := Macro "CmdName" $}} |
| {{$synthetic := GetAnnotation $ "synthetic"}} |
| {{$ret := not (IsVoid $.Return.Type)}} |
| {{$spyname := Global "SpyName"}} |
| |
| inline {{Macro "C++.ReturnType" $}} {{$spyname}}::{{$name}}({{Macro "C++.CallParameters" $}}) { |
| GAPID_INFO("{{$name}}()\n"); |
| {{$args := Macro "C++.CallArguments" $}} |
| {{if $ret}} |
| {{if $synthetic}} |
| {{Macro "C++.ReturnType" $}} result = {{Macro "C++.Null" (TypeOf $.Return)}}; |
| {{else}} |
| {{Macro "C++.ReturnType" $}} result = mImports.{{$name}}({{Macro "C++.CallArguments" $}}); |
| {{end}} |
| mState.{{$name}}({{if $args}}{{$args}}, {{end}}result); |
| {{else}} |
| {{if not $synthetic}}mImports.{{$name}}({{$args}});{{end}} |
| mState.{{$name}}({{$args}}); |
| {{end}} |
| ¶ |
| mEncoder->Uint16({{Global "HACK_FUNCTION_INDEX_HACK"}}); // Type ID -- TODO: mEncoder->Id({{Macro "ID" $}}); |
| |
| {{range $p := $.FullParameters}} |
| {{Macro "Encode" "Parameter" $p "Type" (TypeOf $p) "Name" $p.Name}} |
| {{end}} |
| |
| {{if $ret}}¶ |
| return result; |
| {{end}} |
| } |
| {{end}} |
| |
| |
| {{/* |
| ------------------------------------------------------------------------------- |
| Emits the C++ encode logic for the specified parameter. |
| ------------------------------------------------------------------------------- |
| */}} |
| {{define "Encode"}} |
| {{AssertType $.Type "Type"}} |
| {{AssertType $.Name "string"}} |
| {{AssertType $.Parameter "Parameter"}} |
| |
| {{ if IsPseudonym $.Type}}{{Macro "Encode" "Type" $.Type.To "Name" $.Name "Parameter" $.Parameter}} |
| {{else if IsBool $.Type}}mEncoder->Bool({{$.Name}}); |
| {{else if IsU8 $.Type}}mEncoder->Uint8({{$.Name}}); |
| {{else if IsS8 $.Type}}mEncoder->Int8({{$.Name}}); |
| {{else if IsU16 $.Type}}mEncoder->Uint16({{$.Name}}); |
| {{else if IsS16 $.Type}}mEncoder->Int16({{$.Name}}); |
| {{else if IsF32 $.Type}}mEncoder->Float32({{$.Name}}); |
| {{else if IsU32 $.Type}}mEncoder->Uint32({{$.Name}}); |
| {{else if IsS32 $.Type}}mEncoder->Int32({{$.Name}}); |
| {{else if IsF64 $.Type}}mEncoder->Float64({{$.Name}}); |
| {{else if IsU64 $.Type}}mEncoder->Uint64({{$.Name}}); |
| {{else if IsS64 $.Type}}mEncoder->Int64({{$.Name}}); |
| {{else if IsInt $.Type}}mEncoder->Int64({{$.Name}}); |
| {{else if IsUint $.Type}}mEncoder->Uint64({{$.Name}}); |
| {{else if IsPointer $.Type}}mEncoder->Uint64(reinterpret_cast<uint64_t>({{$.Name}})); |
| {{else if IsString $.Type}}mEncoder->String({{$.Name}}); |
| {{else if IsEnum $.Type}}mEncoder->Uint32(static_cast<uint32_t>({{$.Name}})); |
| {{else if IsStaticArray $.Type}} |
| for (int i = 0; i < {{$.Type.Size}}; i++) { |
| {{Macro "Encode" "Type" $.Type.ValueType "Name" (print $.Name "[i]") "Parameter" $.Parameter}} |
| } |
| {{else if IsClass $.Type}} |
| mEncoder->Uint64(0); // CreatedAt |
| {{range $f := $.Type.Fields}} |
| {{Macro "Encode" "Type" $f.Type "Name" (print $.Name ".m" $f.Name) "Parameter" $.Parameter}} |
| {{end}} |
| {{else}}{{Error "Encode passed unsupported type: %s" $.Type.Name}} |
| {{end}} |
| {{end}} |
| |