Upstream version 7.35.144.0
[platform/framework/web/crosswalk.git] / src / ppapi / cpp / extensions / ext_output_traits.h
1 // Copyright (c) 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #ifndef PPAPI_CPP_EXTENSIONS_OUTPUT_TRAITS_H_
6 #define PPAPI_CPP_EXTENSIONS_OUTPUT_TRAITS_H_
7
8 #include <vector>
9
10 #include "ppapi/c/pp_var.h"
11 #include "ppapi/cpp/extensions/from_var_converter.h"
12 #include "ppapi/cpp/logging.h"
13 #include "ppapi/cpp/pass_ref.h"
14 #include "ppapi/cpp/var.h"
15 #include "ppapi/cpp/var_array.h"
16
17 namespace pp {
18 namespace ext {
19 namespace internal {
20
21 template <class T>
22 class VarOutputAdapterWithStorage {
23  public:
24   VarOutputAdapterWithStorage() : pp_var_(PP_MakeUndefined()) {
25   }
26
27   ~VarOutputAdapterWithStorage() {
28     PP_DCHECK(pp_var_.type == PP_VARTYPE_UNDEFINED);
29   }
30
31   PP_Var& pp_var() { return pp_var_; }
32
33   T& output() {
34     Var auto_release(PASS_REF, pp_var_);
35     converter_.Set(pp_var_);
36     pp_var_ = PP_MakeUndefined();
37     return converter_.value();
38   }
39
40  private:
41   PP_Var pp_var_;
42   FromVarConverter<T> converter_;
43
44   // Disallow copying and assignment.
45   VarOutputAdapterWithStorage(const VarOutputAdapterWithStorage<T>&);
46   VarOutputAdapterWithStorage<T>& operator=(
47       const VarOutputAdapterWithStorage<T>&);
48 };
49
50 // ExtCallbackOutputTraits is used with ExtCompletionCallbackWithOutput. Unlike
51 // pp::internal::CallbackOutputTraits, it always uses PP_Var* as output
52 // parameter type to interact with the browser.
53 //
54 // For example, CompletionCallbackWithOutput<double> (using
55 // pp::internal::CallbackOutputTraits) uses double* as the output parameter
56 // type; while ExtCompletionCallbackWithOutput<double> uses PP_Var*.
57 template <class T>
58 struct ExtCallbackOutputTraits {
59   typedef PP_Var* APIArgType;
60   typedef VarOutputAdapterWithStorage<T> StorageType;
61
62   static inline APIArgType StorageToAPIArg(StorageType& t) {
63     return &t.pp_var();
64   }
65
66   // This must be called exactly once to consume the one PP_Var reference
67   // assigned to us by the browser.
68   static inline T& StorageToPluginArg(StorageType& t) {
69     return t.output();
70   }
71
72   static inline void Initialize(StorageType* /* t */) {}
73 };
74
75 // This class provides storage for a PP_Var and a vector of objects which are
76 // of type T. The PP_Var is used as an output parameter to receive an array var
77 // from the browser. Each element in the array var is converted to a T object,
78 // using FromVarConverter, and stores in the vector.
79 template <class T>
80 class ArrayVarOutputAdapterWithStorage {
81  public:
82   ArrayVarOutputAdapterWithStorage() : pp_var_(PP_MakeUndefined()) {
83   }
84
85   ~ArrayVarOutputAdapterWithStorage() {
86     PP_DCHECK(pp_var_.type == PP_VARTYPE_UNDEFINED);
87   }
88
89   PP_Var& pp_var() { return pp_var_; }
90
91   std::vector<T>& output() {
92     PP_DCHECK(output_storage_.empty());
93
94     Var var(PASS_REF, pp_var_);
95     pp_var_ = PP_MakeUndefined();
96     if (var.is_array()) {
97       VarArray array(var);
98
99       uint32_t length = array.GetLength();
100       output_storage_.reserve(length);
101       for (uint32_t i = 0; i < length; ++i) {
102         FromVarConverter<T> converter(array.Get(i).pp_var());
103         output_storage_.push_back(converter.value());
104       }
105     }
106
107     return output_storage_;
108   }
109
110  private:
111   PP_Var pp_var_;
112   std::vector<T> output_storage_;
113
114   // Disallow copying and assignment.
115   ArrayVarOutputAdapterWithStorage(const ArrayVarOutputAdapterWithStorage<T>&);
116   ArrayVarOutputAdapterWithStorage<T>& operator=(
117       const ArrayVarOutputAdapterWithStorage<T>&);
118 };
119
120 template <class T>
121 struct ExtCallbackOutputTraits< std::vector<T> > {
122   typedef PP_Var* APIArgType;
123   typedef ArrayVarOutputAdapterWithStorage<T> StorageType;
124
125   static inline APIArgType StorageToAPIArg(StorageType& t) {
126     return &t.pp_var();
127   }
128
129   // This must be called exactly once to consume the one PP_Var reference
130   // assigned to us by the browser.
131   static inline std::vector<T>& StorageToPluginArg(StorageType& t) {
132     return t.output();
133   }
134
135   static inline void Initialize(StorageType* /* t */) {}
136 };
137
138 }  // namespace internal
139 }  // namespace ext
140 }  // namespace pp
141
142 #endif  // PPAPI_CPP_EXTENSIONS_OUTPUT_TRAITS_H_