blob: 96f52ddfb4ba6f93662002ea3220eb1c8b3fb559 [file] [log] [blame]
Zack Williams41513bf2018-07-07 20:08:35 -07001/*
2 * Copyright 2017-present Open Networking Foundation
3
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7
8 * http://www.apache.org/licenses/LICENSE-2.0
9
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
Stephane Barbarie14088962017-06-01 16:56:55 -040016//package voltha
17package main
18
19/*
20#include <stdlib.h>
21#include "voltha-defs.h"
22 */
23import "C"
24
25import (
26 "log"
27 "golang.org/x/net/context"
28 "google.golang.org/grpc"
29 "github.com/golang/protobuf/ptypes/empty"
30 "github.com/hashicorp/consul/api"
31 pb "github.com/opencord/voltha/netconf/translator/voltha"
32 pb_health "github.com/opencord/voltha/netconf/translator/voltha/health"
33 pb_device "github.com/opencord/voltha/netconf/translator/voltha/device"
34 pb_adapter "github.com/opencord/voltha/netconf/translator/voltha/adapter"
35 pb_logical_device "github.com/opencord/voltha/netconf/translator/voltha/logical_device"
36 pb_openflow "github.com/opencord/voltha/netconf/translator/voltha/openflow_13"
37 pb_any "github.com/golang/protobuf/ptypes/any"
38 "unsafe"
39 "fmt"
40)
41
42const (
43 default_consul_address = "10.100.198.220:8500"
44 default_grpc_address = "localhost:50555"
45 grpc_service_name = "voltha-grpc"
46)
47
48var (
49 GrpcConn *grpc.ClientConn = nil
50 VolthaGlobalClient pb.VolthaGlobalServiceClient = nil
51 HealthClient pb_health.HealthServiceClient = nil
52 ConsulClient *api.Client = nil
53 GrpcServiceAddress string = "localhost:50555"
54)
55
56func init() {
57 ConsulClient = connect_to_consul(default_consul_address)
58 GrpcServiceAddress = get_consul_service_address(grpc_service_name)
59 GrpcConn = connect_to_grpc(GrpcServiceAddress)
60
61 VolthaGlobalClient = pb.NewVolthaGlobalServiceClient(GrpcConn)
62 HealthClient = pb_health.NewHealthServiceClient(GrpcConn)
63}
64
65func connect_to_consul(consul_address string) *api.Client {
66 cfg := api.Config{Address: consul_address }
67
68 log.Printf("Connecting to consul - address: %s", consul_address)
69
70 client, err := api.NewClient(&cfg)
71 if err != nil {
72 panic(err)
73 }
74
75 log.Printf("Connected to consul - address: %s", consul_address)
76
77 return client
78}
79
80func get_consul_service_address(service_name string) string {
81 var service []*api.CatalogService
82 var err error
83
84 log.Printf("Getting consul service - name:%s", service_name)
85
86 if service, _, _ = ConsulClient.Catalog().Service(service_name, "", nil); err != nil {
87 panic(err)
88 }
89
90 address := fmt.Sprintf("%s:%d", service[0].ServiceAddress, service[0].ServicePort)
91
92 log.Printf("Got consul service - name:%s, address:%s", service_name, address)
93
94 return address
95}
96
97func connect_to_grpc(grpc_address string) *grpc.ClientConn {
98 var err error
99 var client *grpc.ClientConn
100
101 log.Printf("Connecting to grpc - address: %s", grpc_address)
102
103 // Set up a connection to the server.
104 client, err = grpc.Dial(grpc_address, grpc.WithInsecure())
105 if err != nil {
106 log.Fatalf("did not connect: %s", err.Error())
107 }
108
109 log.Printf("Connected to grpc - address: %s", grpc_address)
110
111 return client
112}
113// Utility methods
114
115// -------------------------------------------------
116// C to Protobuf conversion methods
117// -------------------------------------------------
118
119func _c_to_proto_Address(address C.isDevice_Address) *pb_device.Device {
120 var device *pb_device.Device
121
122 // Identify the address type to assign
123 switch address.Type {
124 case C.MAC:
125 device.Address = &pb_device.Device_MacAddress{
126 MacAddress: C.GoString(address.Value),
127 }
128 break
129 case C.IPV4:
130 device.Address = &pb_device.Device_Ipv4Address{
131 Ipv4Address: C.GoString(address.Value),
132 }
133 break
134 case C.IPV6:
135 device.Address = &pb_device.Device_Ipv6Address{
136 Ipv6Address: C.GoString(address.Value),
137 }
138 break
139 case C.HOST_AND_PORT:
140 device.Address = &pb_device.Device_HostAndPort{
141 HostAndPort: C.GoString(address.Value),
142 }
143 break
144 }
145
146 return device
147}
148
149// -------------------------------------------------
150// Protobuf to C conversion methods
151// -------------------------------------------------
152
153func _proto_to_c_Adapters(instances []*pb_adapter.Adapter) C.AdapterArray {
154 // TODO: not implemented
155 var result C.AdapterArray
156 return result
157}
158func _proto_to_c_LogicalDevices(instances []*pb_logical_device.LogicalDevice) C.LogicalDeviceArray {
159 // TODO: not implemented
160 var result C.LogicalDeviceArray
161 return result
162}
163func _proto_to_c_DeviceTypes(instances []*pb_device.DeviceType) C.DeviceTypeArray {
164 // TODO: not implemented
165 var result C.DeviceTypeArray
166 return result
167}
168func _proto_to_c_AlarmFilters(instances []*pb.AlarmFilter) C.AlarmFilterArray {
169 // TODO: not implemented
170 var result C.AlarmFilterArray
171 return result
172}
173func _proto_to_c_DeviceGroups(instances []*pb.DeviceGroup) C.DeviceGroupArray {
174 // TODO: not implemented
175 var result C.DeviceGroupArray
176 return result
177}
178func _proto_to_c_ProxyAddress(proxyAddress *pb_device.Device_ProxyAddress) *C.Device_ProxyAddress {
179 // TODO: not implemented
180 var result *C.Device_ProxyAddress
181 defer C.free(unsafe.Pointer(result))
182 return result
183}
184func _proto_to_c_Ports(ports []*pb_device.Port) C.PortArray {
185 // TODO: not implemented
186 var result C.PortArray
187 return result
188}
189func _proto_to_c_Flows(flows *pb_openflow.Flows) *C.Flows {
190 // TODO: not implemented
191 var result *C.Flows
192 defer C.free(unsafe.Pointer(result))
193 return result
194}
195func _proto_to_c_FlowGroups(groups *pb_openflow.FlowGroups) *C.FlowGroups {
196 // TODO: not implemented
197 var result *C.FlowGroups
198 defer C.free(unsafe.Pointer(result))
199 return result
200}
201func _proto_to_c_PmConfigs(configs *pb_device.PmConfigs) *C.PmConfigs {
202 // TODO: not implemented
203 var result *C.PmConfigs
204 defer C.free(unsafe.Pointer(result))
205 return result
206}
207func _proto_to_c_Custom(configs *pb_any.Any) *C.Any {
208 // TODO: not implemented
209 var result *C.Any
210 defer C.free(unsafe.Pointer(result))
211 return result
212}
213func _proto_to_c_HealthStatus(health *pb_health.HealthStatus) C.HealthStatus {
214 var result C.HealthStatus
215
216 var c_string *C.char
217 defer C.free(unsafe.Pointer(c_string))
218
219 if c_string = C.CString(health.GetState().String()); c_string != nil {
220 result.State = c_string
221 }
222
223 return result
224}
225
226func _proto_to_c_VolthaInstances(instances []*pb.VolthaInstance) C.VolthaInstanceArray {
227 var result C.VolthaInstanceArray
228 var c_string *C.char
229 var c_voltha_instance C.VolthaInstance
230 defer C.free(unsafe.Pointer(c_string))
231
232 sizeof := unsafe.Sizeof(c_voltha_instance)
233 count := len(instances)
234 result.size = C.int(count)
235
236 c_items := C.malloc(C.size_t(result.size) * C.size_t(sizeof))
237 defer C.free(unsafe.Pointer(c_items))
238
239 // Array to the allocated space
240 c_array := (*[1<<30 - 1]C.VolthaInstance)(c_items)
241
242 for index, value := range instances {
243 if c_string = C.CString(value.GetInstanceId()); c_string != nil {
244 c_voltha_instance.InstanceId = c_string
245 }
246 if c_string = C.CString(value.GetVersion()); c_string != nil {
247 c_voltha_instance.Version = c_string
248 }
249 if c_string = C.CString(value.GetLogLevel().String()); c_string != nil {
250 c_voltha_instance.LogLevel = c_string
251 }
252 c_voltha_instance.Health = _proto_to_c_HealthStatus(value.GetHealth())
253 c_voltha_instance.Adapters = _proto_to_c_Adapters(value.GetAdapters())
254 c_voltha_instance.LogicalDevices = _proto_to_c_LogicalDevices(value.GetLogicalDevices())
255 c_voltha_instance.Devices = _proto_to_c_Devices(value.GetDevices())
256 c_voltha_instance.DeviceTypes = _proto_to_c_DeviceTypes(value.GetDeviceTypes())
257 c_voltha_instance.DeviceGroups = _proto_to_c_DeviceGroups(value.GetDeviceGroups())
258 c_voltha_instance.AlarmFilters = _proto_to_c_AlarmFilters(value.GetAlarmFilters())
259
260 c_array[index] = c_voltha_instance
261 }
262
263 result.items = (*C.VolthaInstance)(unsafe.Pointer(c_array))
264
265 return result
266}
267func _proto_to_c_Devices(instances []*pb_device.Device) C.DeviceArray {
268 var result C.DeviceArray
269 var c_string *C.char
270 var c_device_instance C.Device
271 defer C.free(unsafe.Pointer(c_string))
272
273 sizeof := unsafe.Sizeof(c_device_instance)
274 count := len(instances)
275 result.size = C.int(count)
276
277 c_items := C.malloc(C.size_t(result.size) * C.size_t(sizeof))
278 defer C.free(unsafe.Pointer(c_items))
279
280 c_array := (*[1<<30 - 1]C.Device)(c_items)
281
282 for index, value := range instances {
283 c_array[index] = _proto_to_c_Device(value)
284 }
285
286 result.items = (*C.Device)(unsafe.Pointer(c_array))
287
288 return result
289}
290func _proto_to_c_Voltha(voltha *pb.Voltha) C.Voltha {
291 var result C.Voltha
292 var c_string *C.char
293 defer C.free(unsafe.Pointer(c_string))
294
295 if c_string = C.CString(voltha.GetVersion()); c_string != nil {
296 result.Version = c_string
297 }
298 if c_string = C.CString(voltha.GetLogLevel().String()); c_string != nil {
299 result.LogLevel = c_string
300 }
301
302 result.Instances = _proto_to_c_VolthaInstances(voltha.GetInstances())
303 result.Adapters = _proto_to_c_Adapters(voltha.GetAdapters())
304 result.LogicalDevices = _proto_to_c_LogicalDevices(voltha.GetLogicalDevices())
305 result.Devices = _proto_to_c_Devices(voltha.GetDevices())
306 result.DeviceGroups = _proto_to_c_DeviceGroups(voltha.GetDeviceGroups())
307
308 return result
309}
310
311func _proto_to_c_Address(device *pb_device.Device) C.isDevice_Address {
312 var address C.isDevice_Address
313 var c_string *C.char
314 defer C.free(unsafe.Pointer(c_string))
315
316 switch device.GetAddress().(type) {
317 case *pb_device.Device_MacAddress:
318 address.Type = C.MAC
319 c_string = C.CString(device.GetMacAddress())
320 address.Value = c_string
321 case *pb_device.Device_Ipv4Address:
322 address.Type = C.IPV4
323 c_string = C.CString(device.GetIpv4Address())
324 address.Value = c_string
325 case *pb_device.Device_Ipv6Address:
326 address.Type = C.IPV6
327 c_string = C.CString(device.GetIpv6Address())
328 address.Value = c_string
329 case *pb_device.Device_HostAndPort:
330 address.Type = C.HOST_AND_PORT
331 c_string = C.CString(device.GetHostAndPort())
332 address.Value = c_string
333 }
334 return address
335}
336
337func _proto_to_c_Device(device *pb_device.Device) C.Device {
338 var result C.Device
339 var c_string *C.char
340 defer C.free(unsafe.Pointer(c_string))
341
342 if c_string = C.CString(device.GetId()); c_string != nil {
343 result.Id = c_string
344 }
345 if c_string = C.CString(device.GetType()); c_string != nil {
346 result.Type = c_string
347 }
348 if device.GetRoot() {
349 result.Root = C.int(1)
350 } else {
351 result.Root = C.int(0)
352 }
353 if c_string = C.CString(device.GetParentId()); c_string != nil {
354 result.ParentId = c_string
355 }
356
357 result.ParentPortNo = C.uint32_t(device.GetParentPortNo())
358
359 if c_string = C.CString(device.GetVendor()); c_string != nil {
360 result.Vendor = c_string
361 }
362 if c_string = C.CString(device.GetModel()); c_string != nil {
363 result.Model = c_string
364 }
365 if c_string = C.CString(device.GetHardwareVersion()); c_string != nil {
366 result.HardwareVersion = c_string
367 }
368 if c_string = C.CString(device.GetFirmwareVersion()); c_string != nil {
369 result.FirmwareVersion = c_string
370 }
371 if c_string = C.CString(device.GetSoftwareVersion()); c_string != nil {
372 result.SoftwareVersion = c_string
373 }
374 if c_string = C.CString(device.GetSerialNumber()); c_string != nil {
375 result.SerialNumber = c_string
376 }
377 if c_string = C.CString(device.GetAdapter()); c_string != nil {
378 result.Adapter = c_string
379 }
380
381 result.Vlan = C.uint32_t(device.GetVlan())
382 result.ProxyAddress = _proto_to_c_ProxyAddress(device.GetProxyAddress())
383
384 if c_string = C.CString(device.GetAdminState().String()); c_string != nil {
385 result.AdminState = c_string
386 }
387 if c_string = C.CString(device.GetOperStatus().String()); c_string != nil {
388 result.OperStatus = c_string
389 }
390 if c_string = C.CString(device.GetReason()); c_string != nil {
391 result.Reason = c_string
392 }
393 if c_string = C.CString(device.GetConnectStatus().String()); c_string != nil {
394 result.ConnectStatus = c_string
395 }
396
397 result.Custom = _proto_to_c_Custom(device.GetCustom())
398 result.Ports = _proto_to_c_Ports(device.GetPorts())
399 result.Flows = _proto_to_c_Flows(device.GetFlows())
400 result.FlowGroups = _proto_to_c_FlowGroups(device.GetFlowGroups())
401 result.PmConfigs = _proto_to_c_PmConfigs(device.GetPmConfigs())
402 result.Address = _proto_to_c_Address(device)
403
404 return result
405}
406
407// ---------------------------------------------------------
408// Exported methods accessible through the shared library
409// ---------------------------------------------------------
410
411//export GetHealthStatus
412func GetHealthStatus() C.HealthStatus {
413 var output *pb_health.HealthStatus
414 var err error
415
416 if output, err = HealthClient.GetHealthStatus(context.Background(), &empty.Empty{}); output == nil || err != nil {
417 log.Fatalf("Failed to retrieve health status: %s", err.Error())
418 }
419
420 return _proto_to_c_HealthStatus(output)
421}
422
423//export GetVoltha
424func GetVoltha() C.Voltha {
425 var output *pb.Voltha
426 var err error
427 if output, err = VolthaGlobalClient.GetVoltha(context.Background(), &empty.Empty{}); output == nil || err != nil {
428 log.Fatalf("Failed to retrieve voltha information: %s", err.Error())
429 }
430
431 return _proto_to_c_Voltha(output)
432}
433
434//export ListDevices
435func ListDevices() C.DeviceArray {
436 var output *pb_device.Devices
437 var err error
438 if output, err = VolthaGlobalClient.ListDevices(context.Background(), &empty.Empty{});
439 output == nil || err != nil {
440 log.Fatalf("Failed to retrieve voltha information: %s", err.Error())
441 }
442
443 return _proto_to_c_Devices(output.Items)
444}
445
446//export ListVolthaInstances
447func ListVolthaInstances() *C.char {
448 return nil
449}
450
451//export ListLogicalDevices
452func ListLogicalDevices() *C.char {
453 return nil
454}
455
456//export GetLogicalDevice
457func GetLogicalDevice(input *C.char) *C.char {
458 return nil
459}
460
461//export ListLogicalDevicePorts
462func ListLogicalDevicePorts(input *C.char) *C.char {
463 return nil
464}
465
466//export ListLogicalDeviceFlows
467func ListLogicalDeviceFlows(input *C.char) *C.char {
468 return nil
469}
470
471//export CreateDevice
472func CreateDevice(input C.Device) C.Device {
473 log.Printf("Incoming C Device - type:%v, address_type: %v, address_value:%s",
474 C.GoString(input.Type),
475 C.int(input.Address.Type),
476 C.GoString(input.Address.Value),
477 )
478
479 device := _c_to_proto_Address(input.Address)
480 device.Type = C.GoString(input.Type)
481
482 var output *pb_device.Device
483 var err error
484
485 if output, err = VolthaGlobalClient.CreateDevice(context.Background(), device);
486 output == nil || err != nil {
487 log.Fatalf("Failed to create device: %s", err.Error())
488 }
489
490 return _proto_to_c_Device(output)
491}
492
493// Debugging code
494func TestSerialize() {
495 var object C.Device
496
497 object.Type = C.CString("simulated_olt")
498 object.Address.Type = 3
499 object.Address.Value = C.CString("172.16.1.233:123")
500
501 //xmlObject, _ := xml.Marshal(object)
502 //
503 //log.Printf("object: %+v", string(xmlObject))
504
505 CreateDevice(object)
506}
507
508func main() {
509 // We need the main function to make possible
510 // CGO compiler to compile the package as C shared library
511 //TestSerialize()
512}