The Pedigree Project  0.1
Device.h
1 /*
2  * Copyright (c) 2008-2014, Pedigree Developers
3  *
4  * Please see the CONTRIB file in the root of the source tree for a full
5  * list of contributors.
6  *
7  * Permission to use, copy, modify, and distribute this software for any
8  * purpose with or without fee is hereby granted, provided that the above
9  * copyright notice and this permission notice appear in all copies.
10  *
11  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
12  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
13  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
14  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
15  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
16  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
17  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
18  */
19 
20 #ifndef MACHINE_DEVICE_H
21 #define MACHINE_DEVICE_H
22 
23 #include "pedigree/kernel/compiler.h"
24 #include "pedigree/kernel/processor/types.h"
25 #include "pedigree/kernel/utilities/String.h"
26 #include "pedigree/kernel/utilities/Vector.h"
27 #ifdef THREADS
28 #include "pedigree/kernel/LockGuard.h"
29 #include "pedigree/kernel/process/Mutex.h"
30 #endif
31 #ifdef OPENFIRMWARE
32 #include "pedigree/kernel/machine/openfirmware/OpenFirmware.h"
33 #endif
34 #include "pedigree/kernel/machine/Pci.h"
35 #include "pedigree/kernel/utilities/utility.h"
36 
37 class IoBase;
38 
44 {
45  public:
46  typedef Device *(*Callback)(Device *);
47 
50  enum Type
51  {
53  Root,
54  Disk,
55  Bus,
56  Display,
58  Network,
62  Mouse,
63  Controller,
65  UsbController,
68  UsbContainer,
69  };
73  class Address
74  {
75  public:
78  Address(
79  const String &n, uintptr_t a, size_t s, bool io, size_t pad = 1);
80  ~Address();
82  void
83  map(size_t forcedSize = 0, bool bUser = false,
84  bool bWriteCombine = false, bool bWriteThrough = false);
89  uintptr_t m_Address;
91  size_t m_Size;
100  size_t m_Padding;
101 
102  private:
103  Address(const Address &);
104  Address &operator=(const Address &);
105 
106  bool m_bMapped;
107  };
108 
109  Device();
115  Device(Device *p);
116  virtual ~Device();
117 
140  static void foreach (Callback callback, Device *root = 0);
141  template <class F, class... Args>
142  static void foreach (
143  pedigree_std::Callable<F> &callback, Device * root, Args... args);
144 
146  static void addToRoot(Device *device);
147 
149  inline Device *getParent() const
150  {
151  return m_pParent;
152  }
154  inline void setParent(Device *p)
155  {
156  m_pParent = p;
157  }
158 
160  virtual void getName(String &str);
161 
163  virtual Type getType()
164  {
165  return Root;
166  }
167 
170  {
171  return m_SpecificType;
172  }
174  virtual void setSpecificType(String str)
175  {
176  m_SpecificType = pedigree_std::move(str);
177  }
178 
180  void setPciPosition(uint32_t bus, uint32_t device, uint32_t func)
181  {
182  m_PciBusPos = bus;
183  m_PciDevicePos = device;
184  m_PciFunctionNum = func;
185  }
189  uint8_t classCode, uint8_t subclassCode, uint16_t vendorId,
190  uint16_t deviceId, uint8_t progIf)
191  {
192  m_ClassCode = classCode;
193  m_SubclassCode = subclassCode;
194  m_VendorId = vendorId;
195  m_DeviceId = deviceId;
196  m_ProgInterface = progIf;
197  }
200  {
201  m_ConfigHeader = space;
202  }
205  {
206  return m_ConfigHeader;
207  }
209  inline uint8_t getPciClassCode()
210  {
211  return m_ClassCode;
212  }
214  inline uint8_t getPciSubclassCode()
215  {
216  return m_SubclassCode;
217  }
219  inline uint16_t getPciVendorId()
220  {
221  return m_VendorId;
222  }
224  inline uint16_t getPciDeviceId()
225  {
226  return m_DeviceId;
227  }
229  inline uint8_t getPciProgInterface()
230  {
231  return m_ProgInterface;
232  }
234  inline uint32_t getPciBusPosition()
235  {
236  return m_PciBusPos;
237  }
239  inline uint32_t getPciDevicePosition()
240  {
241  return m_PciDevicePos;
242  }
244  inline uint32_t getPciFunctionNumber()
245  {
246  return m_PciFunctionNum;
247  }
248 
250  virtual void dump(String &str)
251  {
252  str = "Abstract Device";
253  }
254 
257  {
258  return m_Addresses;
259  }
260 
262  virtual uintptr_t getInterruptNumber()
263  {
264  return m_InterruptNumber;
265  }
266 
268  virtual void setInterruptNumber(uintptr_t n)
269  {
270  m_InterruptNumber = n;
271  }
272 
275  void addChild(Device *pDevice);
276 
279  Device *getChild(size_t n);
280 
282  size_t getNumChildren();
283 
286  void removeChild(size_t n);
287 
289  void removeChild(Device *d);
290 
295  void replaceChild(Device *src, Device *dest);
296 
298  static void searchByVendorId(
299  uint16_t vendorId, void (*callback)(Device *), Device *root = 0);
300  static void searchByVendorIdAndDeviceId(
301  uint16_t vendorId, uint16_t deviceId, void (*callback)(Device *),
302  Device *root = 0);
303  static void searchByClass(
304  uint16_t classCode, void (*callback)(Device *), Device *root = 0);
305  static void searchByClassAndSubclass(
306  uint16_t classCode, uint16_t subclassCode, void (*callback)(Device *),
307  Device *root = 0);
308  static void searchByClassSubclassAndProgInterface(
309  uint16_t classCode, uint16_t subclassCode, uint8_t progInterface,
310  void (*callback)(Device *), Device *root = 0);
311 
312 #ifdef OPENFIRMWARE
313 
314  OFHandle getOFHandle()
315  {
316  return m_OfHandle;
317  }
319  void setOFHandle(OFHandle h)
320  {
321  m_OfHandle = h;
322  }
323 #endif
324  private:
326  static void foreachInternal(Callback callback, Device *root);
327  template <class F, class... Args>
328  static void foreachInternal(
329  pedigree_std::Callable<F> &callback, Device *root, Args... args);
331  static void searchByVendorIdInternal(
332  uint16_t vendorId, void (*callback)(Device *), Device *root);
333  static void searchByVendorIdAndDeviceIdInternal(
334  uint16_t vendorId, uint16_t deviceId, void (*callback)(Device *),
335  Device *root);
336  static void searchByClassInternal(
337  uint16_t classCode, void (*callback)(Device *), Device *root);
338  static void searchByClassAndSubclassInternal(
339  uint16_t classCode, uint16_t subclassCode, void (*callback)(Device *),
340  Device *root);
341  static void searchByClassSubclassAndProgInterfaceInternal(
342  uint16_t classCode, uint16_t subclassCode, uint8_t progInterface,
343  void (*callback)(Device *), Device *root);
344 
347  void removeIoMappings();
348 
349  protected:
350  NOT_COPYABLE_OR_ASSIGNABLE(Device);
351 
356  static Device &root()
357  {
358  return m_Root;
359  }
360 
368  static Device m_Root;
370  uintptr_t m_InterruptNumber;
373 #ifdef OPENFIRMWARE
374 
375  OFHandle m_OfHandle;
376 #endif
377 
380  uint8_t m_ClassCode;
382  uint8_t m_SubclassCode;
384  uint16_t m_VendorId;
386  uint16_t m_DeviceId;
389 
391  uint32_t m_PciBusPos;
393  uint32_t m_PciDevicePos;
396 #ifdef THREADS
397 
399 #endif
400 };
401 
402 template <class F, class... Args>
403 void Device::foreach (
404  pedigree_std::Callable<F> &callback, Device * root, Args... args)
405 {
406 #ifdef THREADS
407  LockGuard<Mutex> guard(m_TreeLock);
408 #endif
409 
410  if (!root)
411  {
412  root = &Device::root();
413  }
414 
415  foreachInternal(callback, root, args...);
416 }
417 
418 template <class F, class... Args>
420  pedigree_std::Callable<F> &callback, Device *root, Args... args)
421 {
422  for (size_t i = 0; i < root->getNumChildren();)
423  {
424  // Provide the callback for this child.
425  Device *child = root->getChild(i);
426  Device *result = callback(child, args...);
427  if (!result)
428  {
429  // Remove & skip traversal.
430  root->removeChild(i);
431  delete child;
432  continue;
433  }
434  else if (result != child)
435  {
436  // Replace, but we can still traverse the child.
437  root->replaceChild(child, result);
438  delete child;
439  child = result;
440  }
441 
442  // Traverse this child's tree.
443  foreachInternal(callback, child);
444 
445  ++i;
446  }
447 }
448 
449 #endif
static Mutex m_TreeLock
Definition: Device.h:398
The device is the root of the device tree.
Definition: Device.h:53
void removeChild(size_t n)
Definition: Device.cc:142
virtual void dump(String &str)
Definition: Device.h:250
Device * getChild(size_t n)
Definition: Device.cc:132
String m_SpecificType
Definition: Device.h:372
uintptr_t m_Address
Definition: Device.h:89
uint8_t getPciSubclassCode()
Definition: Device.h:214
uint32_t getPciDevicePosition()
Definition: Device.h:239
size_t getNumChildren()
Definition: Device.cc:137
A vector / dynamic array.
virtual String getSpecificType()
Definition: Device.h:169
String m_Name
Definition: Device.h:86
size_t m_Size
Definition: Device.h:91
A disk device - a block device in UNIX terms.
Definition: Device.h:54
virtual void setInterruptNumber(uintptr_t n)
Definition: Device.h:268
virtual Vector< Address * > & addresses()
Definition: Device.h:256
uint8_t m_ClassCode
Definition: Device.h:380
The device type is not covered by any other value.
Definition: Device.h:52
size_t m_Padding
Definition: Device.h:100
Device * m_pParent
Definition: Device.h:366
Definition: Mutex.h:58
uint8_t m_ProgInterface
Definition: Device.h:388
uint32_t m_PciBusPos
Definition: Device.h:391
PciBus::ConfigSpace m_ConfigHeader
Definition: Device.h:378
Definition: String.h:49
PciBus::ConfigSpace getPciConfigHeader() const
Definition: Device.h:204
uint16_t m_DeviceId
Definition: Device.h:386
Abstrace base class for hardware I/O capabilities.
Definition: IoBase.h:31
uint32_t m_PciDevicePos
Definition: Device.h:393
void replaceChild(Device *src, Device *dest)
Definition: Device.cc:168
uint32_t getPciBusPosition()
Definition: Device.h:234
virtual uintptr_t getInterruptNumber()
Definition: Device.h:262
Definition: Device.h:43
bool m_IsIoSpace
Definition: Device.h:94
uint32_t getPciFunctionNumber()
Definition: Device.h:244
Definition: Bus.h:31
uint16_t m_VendorId
Definition: Device.h:384
Same as Generic, but for USB devices.
Definition: Device.h:67
virtual void setSpecificType(String str)
Definition: Device.h:174
static Device & root()
Definition: Device.h:356
uint8_t getPciProgInterface()
Definition: Device.h:229
void setPciPosition(uint32_t bus, uint32_t device, uint32_t func)
Definition: Device.h:180
A device that can play sounds.
Definition: Device.h:60
uint32_t m_PciFunctionNum
Definition: Device.h:395
uint16_t getPciDeviceId()
Definition: Device.h:224
void setParent(Device *p)
Definition: Device.h:154
static void foreach(Callback callback, Device *root=0)
Definition: Device.cc:94
IoBase * m_Io
Definition: Device.h:97
uintptr_t m_InterruptNumber
Definition: Device.h:370
Vector< Address * > m_Addresses
Definition: Device.h:362
void setPciIdentifiers(uint8_t classCode, uint8_t subclassCode, uint16_t vendorId, uint16_t deviceId, uint8_t progIf)
Definition: Device.h:188
virtual Type getType()
Definition: Device.h:163
void setPciConfigHeader(const PciBus::ConfigSpace &space)
Definition: Device.h:199
uint8_t getPciClassCode()
Definition: Device.h:209
A keyboard-like human interface device.
Definition: Device.h:61
Type
Definition: Device.h:50
Device * getParent() const
Definition: Device.h:149
static void foreachInternal(Callback callback, Device *root)
Vector< Device * > m_Children
Definition: Device.h:364
uint16_t getPciVendorId()
Definition: Device.h:219
static Device m_Root
Definition: Device.h:368
uint8_t m_SubclassCode
Definition: Device.h:382