Commit e74f305b5d49d5e329db67eebe985476777b9593
1 parent
5e054e6e
Exists in
master
and in
1 other branch
Adding dynamic typed properties on local session object.
Showing
8 changed files
with
434 additions
and
1 deletions
Show diff stats
client/ipcclient.cbp
@@ -45,6 +45,7 @@ | @@ -45,6 +45,7 @@ | ||
45 | <Unit filename="src/core/constants.cc" /> | 45 | <Unit filename="src/core/constants.cc" /> |
46 | <Unit filename="src/core/events.cc" /> | 46 | <Unit filename="src/core/events.cc" /> |
47 | <Unit filename="src/core/linux/request.cc" /> | 47 | <Unit filename="src/core/linux/request.cc" /> |
48 | + <Unit filename="src/core/property.cc" /> | ||
48 | <Unit filename="src/core/session.cc" /> | 49 | <Unit filename="src/core/session.cc" /> |
49 | <Unit filename="src/core/windows/pop.cc" /> | 50 | <Unit filename="src/core/windows/pop.cc" /> |
50 | <Unit filename="src/core/windows/push.cc" /> | 51 | <Unit filename="src/core/windows/push.cc" /> |
@@ -55,6 +56,7 @@ | @@ -55,6 +56,7 @@ | ||
55 | <Unit filename="src/host/init.cc" /> | 56 | <Unit filename="src/host/init.cc" /> |
56 | <Unit filename="src/host/pop.cc" /> | 57 | <Unit filename="src/host/pop.cc" /> |
57 | <Unit filename="src/host/private.h" /> | 58 | <Unit filename="src/host/private.h" /> |
59 | + <Unit filename="src/host/properties.cc" /> | ||
58 | <Unit filename="src/host/push.cc" /> | 60 | <Unit filename="src/host/push.cc" /> |
59 | <Unit filename="src/host/states.cc" /> | 61 | <Unit filename="src/host/states.cc" /> |
60 | <Unit filename="src/host/stream.cc" /> | 62 | <Unit filename="src/host/stream.cc" /> |
@@ -0,0 +1,212 @@ | @@ -0,0 +1,212 @@ | ||
1 | +/* | ||
2 | + * "Software pw3270, desenvolvido com base nos códigos fontes do WC3270 e X3270 | ||
3 | + * (Paul Mattes Paul.Mattes@usa.net), de emulação de terminal 3270 para acesso a | ||
4 | + * aplicativos mainframe. Registro no INPI sob o nome G3270. | ||
5 | + * | ||
6 | + * Copyright (C) <2008> <Banco do Brasil S.A.> | ||
7 | + * | ||
8 | + * Este programa é software livre. Você pode redistribuí-lo e/ou modificá-lo sob | ||
9 | + * os termos da GPL v.2 - Licença Pública Geral GNU, conforme publicado pela | ||
10 | + * Free Software Foundation. | ||
11 | + * | ||
12 | + * Este programa é distribuído na expectativa de ser útil, mas SEM QUALQUER | ||
13 | + * GARANTIA; sem mesmo a garantia implícita de COMERCIALIZAÇÃO ou de ADEQUAÇÃO | ||
14 | + * A QUALQUER PROPÓSITO EM PARTICULAR. Consulte a Licença Pública Geral GNU para | ||
15 | + * obter mais detalhes. | ||
16 | + * | ||
17 | + * Você deve ter recebido uma cópia da Licença Pública Geral GNU junto com este | ||
18 | + * programa; se não, escreva para a Free Software Foundation, Inc., 51 Franklin | ||
19 | + * St, Fifth Floor, Boston, MA 02110-1301 USA | ||
20 | + * | ||
21 | + * Este programa está nomeado como - e possui - linhas de código. | ||
22 | + * | ||
23 | + * Contatos: | ||
24 | + * | ||
25 | + * perry.werneck@gmail.com (Alexandre Perry de Souza Werneck) | ||
26 | + * erico.mendonca@gmail.com (Erico Mascarenhas Mendonça) | ||
27 | + * | ||
28 | + */ | ||
29 | + | ||
30 | +/** | ||
31 | + * @file src/core/property.cc | ||
32 | + * | ||
33 | + * @brief Implements type independent property object. | ||
34 | + * | ||
35 | + * @author perry.werneck@gmail.com | ||
36 | + * | ||
37 | + */ | ||
38 | + | ||
39 | + #include <ipc-client-internals.h> | ||
40 | + #include <string> | ||
41 | + #include <cstring> | ||
42 | + #include <stdexcept> | ||
43 | + | ||
44 | + using std::runtime_error; | ||
45 | + | ||
46 | +/*---[ Implement ]----------------------------------------------------------------------------------*/ | ||
47 | + | ||
48 | + namespace TN3270 { | ||
49 | + | ||
50 | + class StringProperty : public Property, std::string { | ||
51 | + public: | ||
52 | + StringProperty(const char *str) : Property(Property::String), std::string(str) { | ||
53 | + } | ||
54 | + | ||
55 | + StringProperty(const std::string &str) : Property(Property::String), std::string(str) { | ||
56 | + } | ||
57 | + | ||
58 | + std::string toString() const override { | ||
59 | + return std::string(this->c_str()); | ||
60 | + } | ||
61 | + | ||
62 | + int32_t toInt32() const override { | ||
63 | + return (int32_t) atoi(this->c_str()); | ||
64 | + } | ||
65 | + | ||
66 | + uint32_t toUint32() const override { | ||
67 | + return (uint32_t) atoi(this->c_str()); | ||
68 | + } | ||
69 | + | ||
70 | + bool toBool() const override { | ||
71 | + return atoi(this->c_str()) != 0; | ||
72 | + } | ||
73 | + | ||
74 | + }; | ||
75 | + | ||
76 | + Property::Property(Property::Type type) { | ||
77 | + this->type = type; | ||
78 | + | ||
79 | + } | ||
80 | + | ||
81 | + Property::~Property() { | ||
82 | + } | ||
83 | + | ||
84 | + std::string Property::toString() const { | ||
85 | + throw runtime_error("The value can't be converted to string"); | ||
86 | + } | ||
87 | + | ||
88 | + int32_t Property::toInt32() const { | ||
89 | + throw runtime_error("The value can't be converted to a signed integer"); | ||
90 | + } | ||
91 | + | ||
92 | + uint32_t Property::toUint32() const { | ||
93 | + throw runtime_error("The value can't be converted to an unsigned integer"); | ||
94 | + } | ||
95 | + | ||
96 | + bool Property::toBool() const { | ||
97 | + throw runtime_error("The value can't be converted to boolean"); | ||
98 | + } | ||
99 | + | ||
100 | + | ||
101 | + Property * Property::create(const char *str) { | ||
102 | + return new StringProperty(str); | ||
103 | + } | ||
104 | + | ||
105 | + Property * Property::create(const std::string &str) { | ||
106 | + return new StringProperty(str); | ||
107 | + } | ||
108 | + | ||
109 | + Property * Property::create(const int value) { | ||
110 | + | ||
111 | + class Value : public Property { | ||
112 | + private: | ||
113 | + int32_t value; | ||
114 | + | ||
115 | + public: | ||
116 | + Value(int value) : Property(Property::Int32) { | ||
117 | + this->value = (int32_t) value; | ||
118 | + } | ||
119 | + | ||
120 | + std::string toString() const override { | ||
121 | + return std::to_string(value); | ||
122 | + } | ||
123 | + | ||
124 | + int32_t toInt32() const override { | ||
125 | + return (int32_t) value; | ||
126 | + } | ||
127 | + | ||
128 | + uint32_t toUint32() const override { | ||
129 | + return (uint32_t) value; | ||
130 | + } | ||
131 | + | ||
132 | + bool toBool() const override { | ||
133 | + return value != 0; | ||
134 | + } | ||
135 | + | ||
136 | + }; | ||
137 | + | ||
138 | + return new Value(value); | ||
139 | + | ||
140 | + } | ||
141 | + | ||
142 | + Property * Property::create(const unsigned int value) { | ||
143 | + | ||
144 | + class Value : public Property { | ||
145 | + private: | ||
146 | + uint32_t value; | ||
147 | + | ||
148 | + public: | ||
149 | + Value(unsigned int value) : Property(Property::Uint32) { | ||
150 | + this->value = (uint32_t) value; | ||
151 | + } | ||
152 | + | ||
153 | + std::string toString() const override { | ||
154 | + return std::to_string(value); | ||
155 | + } | ||
156 | + | ||
157 | + int32_t toInt32() const override { | ||
158 | + return (int32_t) value; | ||
159 | + } | ||
160 | + | ||
161 | + uint32_t toUint32() const override { | ||
162 | + return (uint32_t) value; | ||
163 | + } | ||
164 | + | ||
165 | + bool toBool() const override { | ||
166 | + return value != 0; | ||
167 | + } | ||
168 | + | ||
169 | + }; | ||
170 | + | ||
171 | + return new Value(value); | ||
172 | + | ||
173 | + } | ||
174 | + | ||
175 | + Property * Property::create(const bool value) { | ||
176 | + | ||
177 | + class Value : public Property { | ||
178 | + private: | ||
179 | + bool value; | ||
180 | + | ||
181 | + public: | ||
182 | + Value(bool value) : Property(Property::Boolean) { | ||
183 | + this->value = value; | ||
184 | + } | ||
185 | + | ||
186 | + std::string toString() const override { | ||
187 | + return std::to_string(value); | ||
188 | + } | ||
189 | + | ||
190 | + int32_t toInt32() const override { | ||
191 | + return (int32_t) value; | ||
192 | + } | ||
193 | + | ||
194 | + uint32_t toUint32() const override { | ||
195 | + return (uint32_t) value; | ||
196 | + } | ||
197 | + | ||
198 | + bool toBool() const override { | ||
199 | + return value; | ||
200 | + } | ||
201 | + | ||
202 | + }; | ||
203 | + | ||
204 | + return new Value(value); | ||
205 | + | ||
206 | + } | ||
207 | + | ||
208 | + | ||
209 | + } | ||
210 | + | ||
211 | + | ||
212 | + |
client/src/core/session.cc
@@ -0,0 +1,50 @@ | @@ -0,0 +1,50 @@ | ||
1 | +/* | ||
2 | + * "Software pw3270, desenvolvido com base nos códigos fontes do WC3270 e X3270 | ||
3 | + * (Paul Mattes Paul.Mattes@usa.net), de emulação de terminal 3270 para acesso a | ||
4 | + * aplicativos mainframe. Registro no INPI sob o nome G3270. | ||
5 | + * | ||
6 | + * Copyright (C) <2008> <Banco do Brasil S.A.> | ||
7 | + * | ||
8 | + * Este programa é software livre. Você pode redistribuí-lo e/ou modificá-lo sob | ||
9 | + * os termos da GPL v.2 - Licença Pública Geral GNU, conforme publicado pela | ||
10 | + * Free Software Foundation. | ||
11 | + * | ||
12 | + * Este programa é distribuído na expectativa de ser útil, mas SEM QUALQUER | ||
13 | + * GARANTIA; sem mesmo a garantia implícita de COMERCIALIZAÇÃO ou de ADEQUAÇÃO | ||
14 | + * A QUALQUER PROPÓSITO EM PARTICULAR. Consulte a Licença Pública Geral GNU para | ||
15 | + * obter mais detalhes. | ||
16 | + * | ||
17 | + * Você deve ter recebido uma cópia da Licença Pública Geral GNU junto com este | ||
18 | + * programa; se não, escreva para a Free Software Foundation, Inc., 51 Franklin | ||
19 | + * St, Fifth Floor, Boston, MA 02110-1301 USA | ||
20 | + * | ||
21 | + * Este programa está nomeado como - e possui - linhas de código. | ||
22 | + * | ||
23 | + * Contatos: | ||
24 | + * | ||
25 | + * perry.werneck@gmail.com (Alexandre Perry de Souza Werneck) | ||
26 | + * erico.mendonca@gmail.com (Erico Mascarenhas Mendonça) | ||
27 | + * | ||
28 | + */ | ||
29 | + | ||
30 | +/** | ||
31 | + * @file | ||
32 | + * | ||
33 | + * @brief | ||
34 | + * | ||
35 | + * @author perry.werneck@gmail.com | ||
36 | + * | ||
37 | + */ | ||
38 | + | ||
39 | + #include "private.h" | ||
40 | + | ||
41 | +/*---[ Implement ]----------------------------------------------------------------------------------*/ | ||
42 | + | ||
43 | +TN3270::Property * TN3270::Host::operator[](const char *name) const { | ||
44 | + | ||
45 | + if(!this->session) | ||
46 | + throw std::system_error(ENODATA, std::system_category()); | ||
47 | + | ||
48 | + return this->session->getProperty(name); | ||
49 | + | ||
50 | +} |
client/src/include/lib3270/ipc.h
@@ -241,6 +241,58 @@ | @@ -241,6 +241,58 @@ | ||
241 | KYBD_UNLOCK, ///< @brief Unlock the keyboard if it was locked by operator error. | 241 | KYBD_UNLOCK, ///< @brief Unlock the keyboard if it was locked by operator error. |
242 | }; | 242 | }; |
243 | 243 | ||
244 | + /// @brief Dynamic Data type | ||
245 | + class TN3270_PUBLIC Property { | ||
246 | + public: | ||
247 | + | ||
248 | + /// @brief IPC Data type. | ||
249 | + enum Type : uint8_t { | ||
250 | + String = 's', | ||
251 | + Boolean = 'b', | ||
252 | + Uchar = 'y', | ||
253 | + Int16 = 'n', | ||
254 | + Uint16 = 'q', | ||
255 | + Int32 = 'i', | ||
256 | + Int32x = 'h', | ||
257 | + Uint32 = 'u', | ||
258 | + Int64 = 'x', | ||
259 | + Uint64 = 't' | ||
260 | + }; | ||
261 | + | ||
262 | + private: | ||
263 | + Type type; | ||
264 | + | ||
265 | + protected: | ||
266 | + Property(Type type); | ||
267 | + | ||
268 | + public: | ||
269 | + inline bool operator==(Type type) const noexcept { | ||
270 | + return this->type == type; | ||
271 | + } | ||
272 | + | ||
273 | + static Property * create(const char *str); | ||
274 | + static Property * create(const std::string &str); | ||
275 | + static Property * create(const int value); | ||
276 | + static Property * create(const unsigned int value); | ||
277 | + static Property * create(const bool value); | ||
278 | + | ||
279 | + inline Type getType() const { | ||
280 | + return this->type; | ||
281 | + } | ||
282 | + | ||
283 | + inline operator Type() const { | ||
284 | + return this->type; | ||
285 | + } | ||
286 | + | ||
287 | + virtual std::string toString() const; | ||
288 | + virtual int32_t toInt32() const; | ||
289 | + virtual uint32_t toUint32() const; | ||
290 | + virtual bool toBool() const; | ||
291 | + | ||
292 | + virtual ~Property(); | ||
293 | + | ||
294 | + }; | ||
295 | + | ||
244 | /// @brief TN3270 Session. | 296 | /// @brief TN3270 Session. |
245 | class TN3270_PUBLIC Session { | 297 | class TN3270_PUBLIC Session { |
246 | protected: | 298 | protected: |
@@ -351,6 +403,7 @@ | @@ -351,6 +403,7 @@ | ||
351 | LIB3270_KEYBOARD_LOCK_STATE input(const std::string &str, const char control_char = '@'); | 403 | LIB3270_KEYBOARD_LOCK_STATE input(const std::string &str, const char control_char = '@'); |
352 | 404 | ||
353 | // Properties. | 405 | // Properties. |
406 | + virtual Property * getProperty(const char *name) const; | ||
354 | virtual void getProperty(const char *name, int &value) const = 0; | 407 | virtual void getProperty(const char *name, int &value) const = 0; |
355 | virtual void getProperty(const char *name, unsigned int &value) const = 0; | 408 | virtual void getProperty(const char *name, unsigned int &value) const = 0; |
356 | virtual void getProperty(const char *name, std::string &value) const = 0; | 409 | virtual void getProperty(const char *name, std::string &value) const = 0; |
@@ -582,6 +635,7 @@ | @@ -582,6 +635,7 @@ | ||
582 | 635 | ||
583 | 636 | ||
584 | // Get properties | 637 | // Get properties |
638 | + Property * operator[](const char *name) const; | ||
585 | 639 | ||
586 | /// @brief Get lib3270 version. | 640 | /// @brief Get lib3270 version. |
587 | inline std::string getVersion() const { | 641 | inline std::string getVersion() const { |
client/src/session/local/private.h
@@ -113,6 +113,7 @@ | @@ -113,6 +113,7 @@ | ||
113 | SSLState getSSLState() const override; | 113 | SSLState getSSLState() const override; |
114 | 114 | ||
115 | // Properties. | 115 | // Properties. |
116 | + Property * getProperty(const char *name) const override; | ||
116 | void getProperty(const char *name, int &value) const override; | 117 | void getProperty(const char *name, int &value) const override; |
117 | void getProperty(const char *name, unsigned int &value) const override; | 118 | void getProperty(const char *name, unsigned int &value) const override; |
118 | void getProperty(const char *name, std::string &value) const override; | 119 | void getProperty(const char *name, std::string &value) const override; |
client/src/session/local/properties.cc
@@ -37,6 +37,7 @@ | @@ -37,6 +37,7 @@ | ||
37 | */ | 37 | */ |
38 | 38 | ||
39 | #include "private.h" | 39 | #include "private.h" |
40 | + #include <lib3270/ipc.h> | ||
40 | #include <lib3270/properties.h> | 41 | #include <lib3270/properties.h> |
41 | #include <lib3270/toggle.h> | 42 | #include <lib3270/toggle.h> |
42 | #include <cstring> | 43 | #include <cstring> |
@@ -45,6 +46,93 @@ | @@ -45,6 +46,93 @@ | ||
45 | 46 | ||
46 | namespace TN3270 { | 47 | namespace TN3270 { |
47 | 48 | ||
49 | + Property * Local::Session::getProperty(const char *name) const { | ||
50 | + | ||
51 | + std::lock_guard<std::mutex> lock(const_cast<Local::Session *>(this)->sync); | ||
52 | + | ||
53 | + // Check for integer properties. | ||
54 | + { | ||
55 | + const LIB3270_INT_PROPERTY * intprop = lib3270_get_int_properties_list(); | ||
56 | + for(size_t ix = 0; intprop[ix].name; ix++) { | ||
57 | + | ||
58 | + if(!strcasecmp(name,intprop[ix].name)) { | ||
59 | + | ||
60 | + errno = 0; | ||
61 | + int value = intprop[ix].get(hSession); | ||
62 | + | ||
63 | + if(errno != 0) { | ||
64 | + throw std::system_error(errno, std::system_category()); | ||
65 | + } | ||
66 | + | ||
67 | + return TN3270::Property::create(value); | ||
68 | + | ||
69 | + } | ||
70 | + | ||
71 | + } | ||
72 | + } | ||
73 | + | ||
74 | + // Check for unsigned int properties | ||
75 | + { | ||
76 | + const LIB3270_UINT_PROPERTY * intprop = lib3270_get_unsigned_properties_list(); | ||
77 | + for(size_t ix = 0; intprop[ix].name; ix++) { | ||
78 | + | ||
79 | + if(!strcasecmp(name,intprop[ix].name)) { | ||
80 | + | ||
81 | + errno = 0; | ||
82 | + unsigned int value = intprop[ix].get(hSession); | ||
83 | + | ||
84 | + if(errno != 0) { | ||
85 | + throw std::system_error(errno, std::system_category()); | ||
86 | + } | ||
87 | + | ||
88 | + return Property::create(value); | ||
89 | + | ||
90 | + } | ||
91 | + | ||
92 | + } | ||
93 | + | ||
94 | + } | ||
95 | + | ||
96 | + // Check for string properties | ||
97 | + { | ||
98 | + const LIB3270_STRING_PROPERTY * strprop = lib3270_get_string_properties_list(); | ||
99 | + | ||
100 | + for(size_t ix = 0; strprop[ix].name; ix++) { | ||
101 | + | ||
102 | + if(!strcasecmp(name,strprop[ix].name)) { | ||
103 | + | ||
104 | + // Found it! | ||
105 | + const char * str = strprop[ix].get(hSession); | ||
106 | + | ||
107 | + if(str) { | ||
108 | + return Property::create(str); | ||
109 | + } | ||
110 | + | ||
111 | + throw std::system_error(errno, std::system_category()); | ||
112 | + | ||
113 | + } | ||
114 | + | ||
115 | + } | ||
116 | + | ||
117 | + } | ||
118 | + | ||
119 | + // Check for boolean properties | ||
120 | + { | ||
121 | + LIB3270_TOGGLE toggle = lib3270_get_toggle_id(name); | ||
122 | + if(toggle != (LIB3270_TOGGLE) -1) { | ||
123 | + | ||
124 | + // Is a Tn3270 toggle, get it! | ||
125 | + return Property::create((bool) lib3270_get_toggle(hSession,toggle)); | ||
126 | + | ||
127 | + } | ||
128 | + | ||
129 | + } | ||
130 | + | ||
131 | + // Not found! | ||
132 | + throw std::system_error(ENOENT, std::system_category()); | ||
133 | + | ||
134 | + } | ||
135 | + | ||
48 | void Local::Session::getProperty(const char *name, int &value) const { | 136 | void Local::Session::getProperty(const char *name, int &value) const { |
49 | 137 | ||
50 | const LIB3270_INT_PROPERTY * intprop = lib3270_get_int_properties_list(); | 138 | const LIB3270_INT_PROPERTY * intprop = lib3270_get_int_properties_list(); |
client/src/testprogram/testprogram.cc
@@ -92,6 +92,10 @@ | @@ -92,6 +92,10 @@ | ||
92 | 92 | ||
93 | try { | 93 | try { |
94 | 94 | ||
95 | + auto version = host["version"]; | ||
96 | + cout << "Property[version]: " << version->toString() << endl; | ||
97 | + delete version; | ||
98 | + | ||
95 | cout | 99 | cout |
96 | << "Version: " << host.getVersion() | 100 | << "Version: " << host.getVersion() |
97 | << "\tRevision: " << host.getRevision() | 101 | << "\tRevision: " << host.getRevision() |
@@ -136,9 +140,28 @@ | @@ -136,9 +140,28 @@ | ||
136 | 140 | ||
137 | } | 141 | } |
138 | 142 | ||
143 | + TN3270::Property * chk() { | ||
144 | + | ||
145 | + class Test : public TN3270::Property { | ||
146 | + private: | ||
147 | + int val; | ||
148 | + | ||
149 | + public: | ||
150 | + Test(int value) : TN3270::Property(TN3270::Property::Uint32) { | ||
151 | + val = value; | ||
152 | + } | ||
153 | + | ||
154 | + virtual ~Test() { } | ||
155 | + }; | ||
156 | + | ||
157 | + return new Test{10}; | ||
158 | + | ||
159 | + } | ||
160 | + | ||
139 | int main(int argc, char **argv) { | 161 | int main(int argc, char **argv) { |
140 | 162 | ||
141 | - const char * session = LIB3270_STRINGIZE_VALUE_OF(PRODUCT_NAME) ":a"; | 163 | + |
164 | + const char * session = ""; // ":a"; | ||
142 | 165 | ||
143 | #pragma GCC diagnostic push | 166 | #pragma GCC diagnostic push |
144 | #pragma GCC diagnostic ignored "-Wzero-as-null-pointer-constant" | 167 | #pragma GCC diagnostic ignored "-Wzero-as-null-pointer-constant" |