1

I have parsed mib using Parser from https://github.com/sleepinggenius2/gosmi package in golang and stored the modules from mib files with below code:

package main

import (
    "fmt"
    "os"
    "path/filepath"

    "github.com/sleepinggenius2/gosmi/parser"
    "github.com/sleepinggenius2/gosmi/types"
)

// Module contains details of a MODULE-IDENTITY
type Module struct {
    Name   string
    Parent types.SmiIdentifier
    OID    types.SmiSubId
    Nodes  map[string]*Node
    Object parser.Module
}

func (m *Module) merge(newModule *Module) {
    // Merge the nodes
    for name, node := range newModule.Nodes {
        if m.Nodes[name] != nil {
            continue
        }
        newNode := *node
        m.Nodes[name] = &newNode
    }
}

var modules = map[string]*Module{}

// Node contains everything inside a MODULE-IDENTITY
type Node struct {
    Name        string
    Parent      types.SmiIdentifier
    OID         types.SmiSubId
    CompleteOID string
    Object      parser.Node
}

func parseNode(node *parser.Node) *Node {
    ret := &Node{
        Name:   node.Name.String(),
        Parent: *node.Oid.SubIdentifiers[0].Name,
        OID:    *node.Oid.SubIdentifiers[1].Number,
        Object: *node,
    }
    return ret
}

func parseModule(module *parser.Module) *Module {
    ret := &Module{
        Nodes:  make(map[string]*Node),
        Object: *module,
    }
    identity := module.Body.Identity
    ret.Name = identity.Name.String()
    ret.Parent = *identity.Oid.SubIdentifiers[0].Name
    ret.OID = *identity.Oid.SubIdentifiers[1].Number
    for _, node := range module.Body.Nodes {
        n := parseNode(&node)
        ret.Nodes[n.Name] = n
    }
    return ret
}

// Init reads all MIBs recursively inside "folder"
// Returns error or nil
func Init(folder string) error {
    var files []string

    err := filepath.Walk(folder, func(path string, info os.FileInfo, err error) error {
        if info.IsDir() {
            return nil
        }
        files = append(files, path)
        return nil
    })
    if err != nil {
        return err
    }

    for _, file := range files {

        module, err := parser.ParseFile(file)
        if err != nil {
            return err
        }

        mod := parseModule(module)

        if modules[mod.Name] == nil {
            modules[mod.Name] = mod
        } else {
            // Merge the modules
            modules[mod.Name].merge(mod)
        }
    }

    return nil
}

func main() {
    Init("/root/testsnmp")
    mod := modules["parallelwirelessTrapMIB"]
    fmt.Println(mod.Name)
    fmt.Println(mod.OID)

}

Also i have started an snmp server in order to listen to traps and print the trap data. One of the thing we receive in the packet is oid. based on that oid received i want to fetch data from the modules parsed.

now two problems I am facing is :

  1. How do I know which module to look into as i have parsed multiple modules and i will have to go into each module in order to decode the OID and fetch exact node.
  2. Is there any builtin library there for use to decode oid and fetch data from parsed module. If not if for example oid is : 2.1.1.4057 then in order to search in tree of modules and nodes what logic would be best for me to decode the oid and fetch 4057 node details from heirarchy of nodes.
  • If you have the MIB files, you can load them using gosmi.LoadModule(), and then later you can get the Node based on the OID using the method gosmi.GetNodeByOID(types.OidMustFromString("")) – nihal Apr 03 '23 at 07:38

0 Answers0