summaryrefslogtreecommitdiffstats
path: root/src/usr/devtree/devtree.H
blob: 128ed7b897e4775f2a99cda3df05107635ff5890 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
/* IBM_PROLOG_BEGIN_TAG                                                   */
/* This is an automatically generated prolog.                             */
/*                                                                        */
/* $Source: src/usr/devtree/devtree.H $                                   */
/*                                                                        */
/* IBM CONFIDENTIAL                                                       */
/*                                                                        */
/* COPYRIGHT International Business Machines Corp. 2013,2014              */
/*                                                                        */
/* p1                                                                     */
/*                                                                        */
/* Object Code Only (OCO) source materials                                */
/* Licensed Internal Code Source Materials                                */
/* IBM HostBoot Licensed Internal Code                                    */
/*                                                                        */
/* The source code for this program is not published or otherwise         */
/* divested of its trade secrets, irrespective of what has been           */
/* deposited with the U.S. Copyright Office.                              */
/*                                                                        */
/* Origin: 30                                                             */
/*                                                                        */
/* IBM_PROLOG_END_TAG                                                     */
/* $IBMCopyrightBlock:
 IBM Confidential

 OCO Source Materials

 5733-907

 (C) Copyright IBM Corp. 2011

 The source code for this program is not published or other-
 wise divested of its trade secrets, irrespective of what has
 been deposited with the U.S. Copyright Office.
$ */
#include <devtree/devtreeif.H>

#ifndef _DEVTREE_H
#define _DEVTREE_H

namespace DEVTREE
{
typedef size_t dtOffset_t;


    /**
     * The devtree class that does the actual work of
     * generating and manipulating the devtree
     *
     */
    class devTree
    {
      public:

        /**
         * Initialize the FDT at address and size
         * @param[in] i_addr     Address to place FDT at
         * @param[in] i_maxSize  Size of FDT
         * @param[in] i_virtual  Address is virtual.
         */
        void initialize(uint64_t i_addr, size_t i_maxSize, bool i_virtual);

        /**
         * Find given node (e.g. "/lpc") in the FDT
         * @param[in] nodePath  NULL terminated string of the path
         * @return dtOffset_t into FDT of node location
         */
        dtOffset_t findNode(const char* nodePath);

        /**
         * Find and return a pointer to a property within a node
         * @param[in] nodeOffset    Offset into FDT to start looking
         * @param[in] propertyName  NULL terminated string of the property
                                    to get
         * @return void* pointer to dtOffset_t into FDT of node location
         */
        void* findProperty(dtOffset_t nodeOffset, const char* propertyName);

        /**
         * Add a new node under the parent node
         * @param[in] parentNode  Offset to parent node
         * @param[in] nodeName    NULL terminated string of node to add
         * @return dtOffset_t into FDT of node location
         */
        dtOffset_t addNode(dtOffset_t parentNode, const char* nodeName);

        /**
         * Add a new node under the parent node with address
         * @param[in] parentNode  Offset to parent node
         * @param[in] nodeName    NULL terminated string of node to add
         * @param[in] unitAddress Address of the node
         * @return dtOffset_t into FDT of node location
         */
       dtOffset_t addNode(dtOffset_t parentNode, const char* nodeName,
                           uint64_t unitAddress);

       /**
        * Add a property to a node with no data
        * @param[in] parentNode    Offset to node to add property to
        * @param[in] propertyName  NULL terminated string of property name
        */
        void addProperty(dtOffset_t parentNode, const char* propertyName);

        /**
         * Add a property to a node with free form bytes
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] propertyData  Data to add
         * @param[in] numBytes  Number of data bytes
         */
        void addPropertyBytes(dtOffset_t parentNode, const char* propertyName,
                              const uint8_t* propertyData, uint32_t numBytes);

        /**
         * Add a property to a node with string data
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] propertyData  NULL terminated string data
         */
        void addPropertyString(dtOffset_t parentNode, const char* propertyName,
                               const char* propertyData);

        /**
         * Add a property to a node with array of strings
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] propertyData  NULL terminated array of strings, last
         *                          string must be NULL
         */
        void addPropertyStrings(dtOffset_t parentNode, const char* propertyName,
                                const char** propertyData);

        /**
         * Add a property to a node with a 32 bit "cell" (aka uint32_t data)
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] cell  Data to add
         */
        void addPropertyCell32(dtOffset_t parentNode, const char* propertyName,
                               const uint32_t cell);

        /**
         * Add a property to a node with a 64 bit "cell" (aka uint64_t data)
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] cell  Data to add
         */
        void addPropertyCell64(dtOffset_t parentNode, const char* propertyName,
                               const uint64_t cell);

        /**
         * Add a property to a node with a 32 bit array of "cells"
         * (aka uint32_t data)
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] cells         Array of uint32_t data
         * @param[in] numCells      Number of cells
         */
        void addPropertyCells32(dtOffset_t parentNode, const char* propertyName,
                                uint32_t cells[], uint32_t numCells);

        /**
         * Add a property to a node with a 64 bit array of "cells"
         * (aka uint64_t data)
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] cells         Array of uint64_t data
         * @param[in] numCells      Number of cells
         */
        void addPropertyCells64(dtOffset_t parentNode, const char* propertyName,
                                uint64_t cells[], uint32_t numCells);

        /**
         * Return the physical "blob" address to the start of the FDT
         * @return uin64_t to the start of the FDT memory
         */
        uint64_t getBlobPhys();

        /**
         * Each devtree node has a "handle" number.  This function returns the
         * handle number for given node.
         * @param[in] nodeOffset    Offset to node
         * @return uin32_t Handle number for node
         */
        uint32_t getPhandle(dtOffset_t nodeOffset);

        /**
         * Append bytes to a property
         * @param[in] parentNode    Offset to node to add property to
         * @param[in] propertyName  NULL terminated string of property name
         * @param[in] propertyData  Data to add
         * @param[in] numBytes  Number of data bytes
         */
       void appendPropertyBytes(dtOffset_t parentNode,
                                 const char* propertyName,
                                 const uint8_t* propertyData,
                                 uint32_t numBytes);

        /**
         * Populate reserved memory regions
         * @param[in] i_addrs    Array of addresses to set in reserved memory
         * @param[in] i_sizes    Array of sizes to set in reserved memory
         * @param[in] i_num      Number of elements in the arrays
         * @return int, zero on sucesses otherwise non zero
         */
       int populateReservedMem(uint64_t i_addrs[],
                               uint64_t i_sizes[],
                               size_t i_num);

       /**
        * Return the current size of the FDT (not max)
        * @return uin32_t Size of the FDT
        */
        uint32_t getSize();


      protected:
        /*Constructor*/
        devTree();

        /*Destructor*/
        ~devTree();

        /**
         * Get the internal struct section at node offset
         * @param[in] offset    Offset to node
         * @return uin32_t* pointer to struct section
         */
       inline uint32_t* getStructSectionAtOffset(dtOffset_t offset);

        /**
         * Utility function to get the length fo the tag/name words for
         * given node
         * @param[in] nodeOffset    Offset to node
         * @return int Words consumed by tag/name in FDT
         */
       int getNodeTagAndNameWords(dtOffset_t nodeOffset);

       /**
        * Utility function to get the length fo the tag/name words for
        * given node
        * @param[in] nodeOffset    Offset to node
        * @return int Words consumed by tag/name in FDT
        */
       void insertStructSpace(uint32_t offset, int numNewWords);

       /**
        * Utility function to shift the string section
        * @param[in] shiftSize  Amount to shift
        */
       void shiftStringsSection(int shiftSize);

       /**
        * Get number of words for property
        * @param[in] propertyOffset  Offset of property
        * @return int Words consumed by Property
        */
      int getPropertyWords(int propertyOffset);

       /**
        * Utility function to add String to string table
        * @param[in] string  NULL terminated string to add
        * @return dtOffset_t Offset string was added at
        */
       dtOffset_t addString(const char *string);

       /**
        * Set the boot CPU PIR into FDT
        * @param[in] pir  PIR value for boot processor
        */
       void setBootCpu(uint32_t pir);

       /**
        * Utility function to locate string in string table
        * @param[in] string  NULL terminated string to find
        * @param[out] stringOffset Offset if found
        * @return bool  True if found
        */
       bool locateStringOffset(const char* string, uint32_t& stringOffset);


      private:

        enum Constants {
            DT_MAGIC            =0xd00dfeed,
            DT_CUR_VERSION      =0x11,
            DT_COMPAT_VERSION   =0x10,

            DT_BEGIN_NODE       =0x1,
            DT_END_NODE         =0x2,
            DT_PROP             =0x3,
            DT_NOP              =0x4,
            DT_END              =0x9,
            DT_INVALID_OFFSET   =0xFFFFFFFF,


            DT_MAX_MEM_RESERVE  =16,

        };


        typedef struct dtHeader
        {
            uint32_t magicNumber;
            uint32_t totalSize;
            uint32_t offsetStruct;
            uint32_t offsetStrings;
            uint32_t offsetReservedMemMap;
            uint32_t version;
            uint32_t lastCompatVersion;
            uint32_t bootCpuId;
            uint32_t sizeStrings;
            uint32_t sizeStruct;
        }
        dtHeader_t;

        typedef struct dtReserveEntry
        {
            uint64_t address;
            uint64_t size;
        }
        dtReserveEntry_t;



        union
        {
            dtHeader_t* mHeader;
            char* mSpace;
        };
        uint32_t mNextPhandle;
        size_t mMaxSize;
        uint64_t mPhysAddr;

        // let my testcase poke around
        friend class devTreeTest;

    };



    uint32_t* devTree::getStructSectionAtOffset(dtOffset_t offset)
    {
        return (uint32_t*) (mSpace + mHeader->offsetStruct + offset);
    }
}
#endif /* _DEVTREE_H */
OpenPOWER on IntegriCloud