]> git.saurik.com Git - apple/xnu.git/blobdiff - iokit/Kernel/IONVRAM.cpp
xnu-1699.22.73.tar.gz
[apple/xnu.git] / iokit / Kernel / IONVRAM.cpp
index b4e86780de77447b010c25d504a33b3c425d5d77..85ac1a2ec01929f0d4a9aa7de3899ef26afbe7d0 100644 (file)
 #include <IOKit/IOPlatformExpert.h>
 #include <IOKit/IOUserClient.h>
 #include <IOKit/IOKitKeys.h>
 #include <IOKit/IOPlatformExpert.h>
 #include <IOKit/IOUserClient.h>
 #include <IOKit/IOKitKeys.h>
+#include <kern/debug.h>
+#include <pexpert/pexpert.h>
 
 #define super IOService
 
 #define kIONVRAMPrivilege      kIOClientPrivilegeAdministrator
 //#define kIONVRAMPrivilege    kIOClientPrivilegeLocalUser
 
 
 #define super IOService
 
 #define kIONVRAMPrivilege      kIOClientPrivilegeAdministrator
 //#define kIONVRAMPrivilege    kIOClientPrivilegeLocalUser
 
-
 OSDefineMetaClassAndStructors(IODTNVRAM, IOService);
 
 bool IODTNVRAM::init(IORegistryEntry *old, const IORegistryPlane *plane)
 OSDefineMetaClassAndStructors(IODTNVRAM, IOService);
 
 bool IODTNVRAM::init(IORegistryEntry *old, const IORegistryPlane *plane)
@@ -203,6 +204,9 @@ void IODTNVRAM::registerNVRAMController(IONVRAMController *nvram)
     _piImage = _nvramImage + _piPartitionOffset;
   }
   
     _piImage = _nvramImage + _piPartitionOffset;
   }
   
+  _lastDeviceSync = 0;
+  _freshInterval = TRUE;               // we will allow sync() even before the first 15 minutes have passed.
+
   initOFVariables();
 }
 
   initOFVariables();
 }
 
@@ -227,27 +231,31 @@ bool IODTNVRAM::serializeProperties(OSSerialize *s) const
   OSDictionary         *dict = 0, *tmpDict = 0;
   OSCollectionIterator *iter = 0;
   
   OSDictionary         *dict = 0, *tmpDict = 0;
   OSCollectionIterator *iter = 0;
   
-  if (_ofDict == 0) return false;
-  
   // Verify permissions.
   hasPrivilege = (kIOReturnSuccess == IOUserClient::clientHasPrivilege(current_task(), kIONVRAMPrivilege));
 
   tmpDict = OSDictionary::withCapacity(1);
   if (tmpDict == 0) return false;
   // Verify permissions.
   hasPrivilege = (kIOReturnSuccess == IOUserClient::clientHasPrivilege(current_task(), kIONVRAMPrivilege));
 
   tmpDict = OSDictionary::withCapacity(1);
   if (tmpDict == 0) return false;
+
+  if (_ofDict == 0) {
+    /* No nvram. Return an empty dictionary. */
+    dict = tmpDict;
+  } else {
+    /* Copy properties with client privilege. */
+    iter = OSCollectionIterator::withCollection(_ofDict);
+    if (iter == 0) return false;
     
     
-  iter = OSCollectionIterator::withCollection(_ofDict);
-  if (iter == 0) return false;
-    
-  while (1) {
-    key = OSDynamicCast(OSSymbol, iter->getNextObject());
-    if (key == 0) break;
+    while (1) {
+      key = OSDynamicCast(OSSymbol, iter->getNextObject());
+      if (key == 0) break;
       
       
-    variablePerm = getOFVariablePerm(key);
-    if ((hasPrivilege || (variablePerm != kOFVariablePermRootOnly)) &&
-       ( ! (variablePerm == kOFVariablePermKernelOnly && current_task() != kernel_task) )) {
-      tmpDict->setObject(key, _ofDict->getObject(key));
+      variablePerm = getOFVariablePerm(key);
+      if ((hasPrivilege || (variablePerm != kOFVariablePermRootOnly)) &&
+         ( ! (variablePerm == kOFVariablePermKernelOnly && current_task() != kernel_task) )) {
+       tmpDict->setObject(key, _ofDict->getObject(key));
+      }
+      dict = tmpDict;
     }
     }
-    dict = tmpDict;
   }
 
   result = dict->serialize(s);
   }
 
   result = dict->serialize(s);
@@ -410,18 +418,32 @@ IOReturn IODTNVRAM::setProperties(OSObject *properties)
     if (object == 0) continue;
     
     if (key->isEqualTo(kIONVRAMDeletePropertyKey)) {
     if (object == 0) continue;
     
     if (key->isEqualTo(kIONVRAMDeletePropertyKey)) {
-      tmpStr = OSDynamicCast(OSString, object);
-      if (tmpStr != 0) {
-       key = OSSymbol::withString(tmpStr);
-       removeProperty(key);
-       key->release();
-       result = true;
-      } else {
-       result = false;
-      }
-    } else {
-      result = setProperty(key, object);
+               tmpStr = OSDynamicCast(OSString, object);
+               if (tmpStr != 0) {
+                       key = OSSymbol::withString(tmpStr);
+                       removeProperty(key);
+                       key->release();
+                       result = true;
+               } else {
+                       result = false;
+               }
+    } else if(key->isEqualTo(kIONVRAMSyncNowPropertyKey)) {
+               tmpStr = OSDynamicCast(OSString, object);
+               if (tmpStr != 0) {
+
+                       result = true; // We are not going to gaurantee sync, this is best effort
+
+                       if(safeToSync())
+                               sync();
+
+               } else {
+                       result = false;
+               }
+       }
+       else {
+               result = setProperty(key, object);
     }
     }
+
   }
   
   iter->release();
   }
   
   iter->release();
@@ -549,7 +571,7 @@ IOReturn IODTNVRAM::writeNVRAMPartition(const OSSymbol *partitionID,
   return kIOReturnSuccess;
 }
 
   return kIOReturnSuccess;
 }
 
-UInt32 IODTNVRAM::savePanicInfo(UInt8 *buffer, IOByteCount length)
+IOByteCount IODTNVRAM::savePanicInfo(UInt8 *buffer, IOByteCount length)
 {
   if ((_piImage == 0) || (length <= 0)) return 0;
   
 {
   if ((_piImage == 0) || (length <= 0)) return 0;
   
@@ -926,6 +948,9 @@ OFVariable gOFVariables[] = {
   {"security-password", kOFVariableTypeData, kOFVariablePermRootOnly, -1},
   {"boot-image", kOFVariableTypeData, kOFVariablePermUserWrite, -1},
   {"com.apple.System.fp-state", kOFVariableTypeData, kOFVariablePermKernelOnly, -1},
   {"security-password", kOFVariableTypeData, kOFVariablePermRootOnly, -1},
   {"boot-image", kOFVariableTypeData, kOFVariablePermUserWrite, -1},
   {"com.apple.System.fp-state", kOFVariableTypeData, kOFVariablePermKernelOnly, -1},
+#if CONFIG_EMBEDDED
+  {"backlight-level", kOFVariableTypeData, kOFVariablePermUserWrite, -1},
+#endif
   {0, kOFVariableTypeData, kOFVariablePermUserRead, -1}
 };
 
   {0, kOFVariableTypeData, kOFVariablePermUserRead, -1}
 };
 
@@ -1112,9 +1137,9 @@ bool IODTNVRAM::convertObjectToProp(UInt8 *buffer, UInt32 *length,
     if (tmpValue == 0xFFFFFFFF) {
       strlcpy((char *)buffer, "-1", *length - propNameLength);
     } else if (tmpValue < 1000) {
     if (tmpValue == 0xFFFFFFFF) {
       strlcpy((char *)buffer, "-1", *length - propNameLength);
     } else if (tmpValue < 1000) {
-      snprintf((char *)buffer, *length - propNameLength, "%ld", tmpValue);
+      snprintf((char *)buffer, *length - propNameLength, "%d", (uint32_t)tmpValue);
     } else {
     } else {
-      snprintf((char *)buffer, *length - propNameLength, "0x%lx", tmpValue);
+      snprintf((char *)buffer, *length - propNameLength, "0x%x", (uint32_t)tmpValue);
     }
     break;
     
     }
     break;
     
@@ -1239,7 +1264,6 @@ enum {
   kMaxNVDataLength = 8
 };
 
   kMaxNVDataLength = 8
 };
 
-#pragma options align=mac68k
 struct NVRAMProperty
 {
   IONVRAMDescriptor   header;
 struct NVRAMProperty
 {
   IONVRAMDescriptor   header;
@@ -1248,7 +1272,6 @@ struct NVRAMProperty
   UInt8               dataLength;
   UInt8               data[ kMaxNVDataLength ];
 };
   UInt8               dataLength;
   UInt8               data[ kMaxNVDataLength ];
 };
-#pragma options align=reset
 
 bool IODTNVRAM::searchNVRAMProperty(IONVRAMDescriptor *hdr, UInt32 *where)
 {
 
 bool IODTNVRAM::searchNVRAMProperty(IONVRAMDescriptor *hdr, UInt32 *where)
 {
@@ -1653,3 +1676,26 @@ IOReturn IODTNVRAM::writeNVRAMPropertyType1(IORegistryEntry *entry,
 
   return ok ? kIOReturnSuccess : kIOReturnNoMemory;
 }
 
   return ok ? kIOReturnSuccess : kIOReturnNoMemory;
 }
+
+bool IODTNVRAM::safeToSync(void)
+{
+    AbsoluteTime delta;
+    UInt64       delta_ns;
+    SInt32       delta_secs;
+       
+       // delta interval went by
+       clock_get_uptime(&delta);
+       
+    // Figure it in seconds.
+    absolutetime_to_nanoseconds(delta, &delta_ns);
+    delta_secs = (SInt32)(delta_ns / NSEC_PER_SEC);
+
+       if ((delta_secs > (_lastDeviceSync + MIN_SYNC_NOW_INTERVAL)) || _freshInterval)
+       {
+               _lastDeviceSync = delta_secs;
+               _freshInterval = FALSE;
+               return TRUE;
+       }
+
+       return FALSE;
+}