1 /*
2 * SPDX-FileCopyrightText: Copyright (c) 1993-2024 NVIDIA CORPORATION & AFFILIATES. All rights reserved.
3 * SPDX-License-Identifier: MIT
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice shall be included in
13 * all copies or substantial portions of the Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23
24 /***************************** HW State Routines ***************************\
25 * *
26 * System Object Function Definitions. *
27 * *
28 \***************************************************************************/
29
30 #include "core/core.h"
31 #include "core/system.h"
32 #include "gpu/gpu.h"
33 #include "gpu_mgr/gpu_mgr.h"
34 #include "core/locks.h"
35 #include "os/os.h"
36 #include "nvrm_registry.h"
37 #include "core/thread_state.h"
38 #include "diagnostics/tracer.h"
39 #include "rmosxfac.h"
40 #include "tls/tls.h"
41 #include "rmapi/rmapi.h"
42 #include "rmapi/client.h"
43 #include "core/hal_mgr.h"
44 #include "nvoc/rtti.h"
45
46 #include "platform/chipset/chipset.h"
47 #include "platform/cpu.h"
48 #include "platform/platform.h"
49 #include "diagnostics/gpu_acct.h"
50 #include "platform/platform_request_handler.h"
51 #include "gpu/external_device/gsync.h"
52 #include "virtualization/kernel_vgpu_mgr.h"
53 #include "mem_mgr/virt_mem_mgr.h"
54 #include "diagnostics/journal.h"
55 #include "virtualization/hypervisor/hypervisor.h"
56 #include "power/gpu_boost_mgr.h"
57 #include "compute/fabric.h"
58 #include "gpu_mgr/gpu_db.h"
59 #include "core/bin_data.h"
60
61 // local static functions
62 static NV_STATUS _sysCreateOs(OBJSYS *);
63 static NV_STATUS _sysCreateChildObjects(OBJSYS *);
64 static void _sysDeleteChildObjects(OBJSYS *);
65 static void _sysNvSwitchDetection(OBJSYS *pSys);
66 static void _sysInitStaticConfig(OBJSYS *pSys);;
67
68 // Global pointer to instance of OBJSYS
69 OBJSYS *g_pSys = NULL;
70
71 typedef struct
72 {
73 NvLength childOffset;
74 const NVOC_CLASS_INFO *pClassInfo;
75 NvBool bDynamicConstruct;
76 } sysChildObject;
77
78 static sysChildObject sysChildObjects[] =
79 {
80 { NV_OFFSETOF(OBJSYS, pHalMgr), classInfo(OBJHALMGR), NV_TRUE },
81 { NV_OFFSETOF(OBJSYS, pPfm), classInfo(OBJPFM), NV_TRUE },
82 { NV_OFFSETOF(OBJSYS, pHypervisor), classInfo(OBJHYPERVISOR), NV_TRUE },
83 { NV_OFFSETOF(OBJSYS, pOS), classInfo(OBJOS), NV_FALSE }, // OS: Wrapper macros must be enabled to use :CONSTRUCT.
84 { NV_OFFSETOF(OBJSYS, pCl), classInfo(OBJCL), NV_TRUE },
85 { NV_OFFSETOF(OBJSYS, pGpuMgr), classInfo(OBJGPUMGR), NV_TRUE },
86 { NV_OFFSETOF(OBJSYS, pGsyncMgr), classInfo(OBJGSYNCMGR), NV_TRUE },
87 { NV_OFFSETOF(OBJSYS, pGpuAcct), classInfo(GpuAccounting), NV_TRUE },
88 { NV_OFFSETOF(OBJSYS, pPlatformRequestHandler), classInfo(PlatformRequestHandler), NV_TRUE },
89 { NV_OFFSETOF(OBJSYS, pRcDB), classInfo(OBJRCDB), NV_TRUE },
90 { NV_OFFSETOF(OBJSYS, pVmm), classInfo(OBJVMM), NV_TRUE },
91 { NV_OFFSETOF(OBJSYS, pKernelVgpuMgr), classInfo(KernelVgpuMgr), NV_TRUE },
92 { NV_OFFSETOF(OBJSYS, pGpuBoostMgr), classInfo(OBJGPUBOOSTMGR), NV_TRUE },
93 { NV_OFFSETOF(OBJSYS, pFabric), classInfo(Fabric), NV_TRUE },
94 { NV_OFFSETOF(OBJSYS, pGpuDb), classInfo(GpuDb), NV_TRUE },
95 };
96
97 static void
_sysDestroyMemExportCache(OBJSYS * pSys)98 _sysDestroyMemExportCache(OBJSYS *pSys)
99 {
100 if (pSys->pSysMemExportModuleLock != NULL)
101 {
102 portSyncRwLockDestroy(pSys->pSysMemExportModuleLock);
103 pSys->pSysMemExportModuleLock = NULL;
104 }
105
106 NV_ASSERT(multimapCountItems(&pSys->sysMemExportCache) == 0);
107
108 multimapDestroy(&pSys->sysMemExportCache);
109 }
110
111 static NV_STATUS
_sysInitMemExportCache(OBJSYS * pSys)112 _sysInitMemExportCache(OBJSYS *pSys)
113 {
114 multimapInit(&pSys->sysMemExportCache, portMemAllocatorGetGlobalNonPaged());
115
116 pSys->pSysMemExportModuleLock =
117 portSyncRwLockCreate(portMemAllocatorGetGlobalNonPaged());
118 if (pSys->pSysMemExportModuleLock == NULL)
119 {
120 _sysDestroyMemExportCache(pSys);
121 return NV_ERR_NO_MEMORY;
122 }
123
124 return NV_OK;
125 }
126
127 static void
_sysDestroyMemExportClient(OBJSYS * pSys)128 _sysDestroyMemExportClient(OBJSYS *pSys)
129 {
130 RM_API *pRmApi;
131
132 if (pSys->hSysMemExportClient == 0)
133 return;
134
135 // Acquire lock to keep rmapiGetInterface() happy.
136 NV_ASSERT(rmapiLockAcquire(API_LOCK_FLAGS_NONE,
137 RM_LOCK_MODULES_DESTROY) == NV_OK);
138
139 pRmApi = rmapiGetInterface(RMAPI_GPU_LOCK_INTERNAL);
140
141 NV_ASSERT(pRmApi->Free(pRmApi, pSys->hSysMemExportClient,
142 pSys->hSysMemExportClient) == NV_OK);
143
144 rmapiLockRelease();
145
146 pSys->hSysMemExportClient = 0;
147 }
148
149 static NV_STATUS
_sysInitMemExportClient(OBJSYS * pSys)150 _sysInitMemExportClient(OBJSYS *pSys)
151 {
152 RM_API *pRmApi;
153 NV_STATUS status;
154
155 // Acquire lock to keep rmapiGetInterface() happy.
156 status = rmapiLockAcquire(API_LOCK_FLAGS_NONE, RM_LOCK_MODULES_INIT);
157 if (status != NV_OK)
158 return status;
159
160 pRmApi = rmapiGetInterface(RMAPI_GPU_LOCK_INTERNAL);
161
162 status = pRmApi->AllocWithHandle(pRmApi, NV01_NULL_OBJECT,
163 NV01_NULL_OBJECT, NV01_NULL_OBJECT,
164 NV01_ROOT, &pSys->hSysMemExportClient,
165 sizeof(pSys->hSysMemExportClient));
166
167 rmapiLockRelease();
168
169 return status;
170 }
171
172 NV_STATUS
sysConstruct_IMPL(OBJSYS * pSys)173 sysConstruct_IMPL(OBJSYS *pSys)
174 {
175 NV_STATUS status;
176 OBJOS *pOS;
177 NvU32 sec = 0;
178 NvU32 uSec = 0;
179
180 g_pSys = pSys;
181
182 RMTRACE_INIT();
183 RMTRACE_INIT_NEW();
184
185 _sysInitStaticConfig(pSys);
186
187 status = _sysCreateChildObjects(pSys);
188 if (status != NV_OK)
189 {
190 goto failed;
191 }
192
193 // Use the monotonic system clock for a unique value
194 pOS = SYS_GET_OS(pSys);
195 osGetCurrentTime(&sec, &uSec);
196 pSys->rmInstanceId = (NvU64)sec * 1000000 + (NvU64)uSec;
197
198 {
199 // Using Hypervisor native interface to detect
200 OBJHYPERVISOR *pHypervisor = SYS_GET_HYPERVISOR(pSys);
201 if (pHypervisor)
202 hypervisorDetection(pHypervisor, pOS);
203 }
204
205 if (!pOS->osRmInitRm(pOS))
206 {
207 status = NV_ERR_GENERIC;
208 goto failed;
209 }
210
211 _sysNvSwitchDetection(pSys);
212
213 // init cpu state
214 RmInitCpuInfo();
215
216 // allocate locks, semaphores, whatever
217 status = rmLocksAlloc(pSys);
218 if (status != NV_OK)
219 goto failed;
220
221 status = threadStateGlobalAlloc();
222 if (status != NV_OK)
223 goto failed;
224
225 status = rmapiInitialize();
226 if (status != NV_OK)
227 goto failed;
228
229 status = _sysInitMemExportCache(pSys);
230 if (status != NV_OK)
231 goto failed;
232
233 status = _sysInitMemExportClient(pSys);
234 if (status != NV_OK)
235 goto failed;
236
237 bindataInitialize();
238
239 return NV_OK;
240
241 failed:
242
243 _sysDestroyMemExportCache(pSys);
244
245 _sysDeleteChildObjects(pSys);
246
247 g_pSys = NULL;
248
249 threadStateGlobalFree();
250
251 rmapiShutdown();
252 rmLocksFree(pSys);
253
254 return status;
255 }
256
257 void
sysDestruct_IMPL(OBJSYS * pSys)258 sysDestruct_IMPL(OBJSYS *pSys)
259 {
260
261 pSys->setProperty(pSys, PDB_PROP_SYS_DESTRUCTING, NV_TRUE);
262
263 _sysDestroyMemExportCache(pSys);
264 _sysDestroyMemExportClient(pSys);
265
266 //
267 // Any of these operations might fail but go ahead and
268 // attempt to free remaining resources before complaining.
269 //
270 listDestroy(&g_clientListBehindGpusLock);
271 listDestroy(&g_userInfoList);
272 multimapDestroy(&g_osInfoList);
273
274 rmapiShutdown();
275 osSyncWithRmDestroy();
276 threadStateGlobalFree();
277 rmLocksFree(pSys);
278
279 //
280 // Free child objects
281 //
282 _sysDeleteChildObjects(pSys);
283
284 g_pSys = NULL;
285
286 RMTRACE_DESTROY();
287 RMTRACE_DESTROY_NEW();
288
289 bindataDestroy();
290 }
291
292 //
293 // Create static system object offspring.
294 //
295 static NV_STATUS
_sysCreateChildObjects(OBJSYS * pSys)296 _sysCreateChildObjects(OBJSYS *pSys)
297 {
298 NV_STATUS status = NV_OK;
299 NvU32 i, n;
300
301 n = NV_ARRAY_ELEMENTS(sysChildObjects);
302
303 for (i = 0; i < n; i++)
304 {
305 if (sysChildObjects[i].bDynamicConstruct)
306 {
307 NvLength offset = sysChildObjects[i].childOffset;
308 Dynamic **ppChild = reinterpretCast(reinterpretCast(pSys, NvU8*) + offset, Dynamic**);
309 Dynamic *pNewObj;
310 status = objCreateDynamic(&pNewObj, pSys, sysChildObjects[i].pClassInfo);
311
312 if (status == NV_OK)
313 {
314 *ppChild = pNewObj;
315 }
316 }
317 else
318 {
319 //
320 // More cases should NOT be added to this list. OBJOS needs to be
321 // cleaned up to use the bDynamicConstruct path then this hack can
322 // be removed.
323 //
324 switch (sysChildObjects[i].pClassInfo->classId)
325 {
326 case classId(OBJOS):
327 status = _sysCreateOs(pSys);
328 break;
329 default:
330 NV_ASSERT(0);
331 status = NV_ERR_INVALID_ARGUMENT;
332 break;
333 }
334 }
335
336 // RMCONFIG: Bail on errors unless the feature/object/engine/class
337 // is simply unsupported
338 if (status == NV_ERR_NOT_SUPPORTED)
339 status = NV_OK;
340 if (status != NV_OK) break;
341 }
342
343 return status;
344 }
345
346 static void
_sysDeleteChildObjects(OBJSYS * pSys)347 _sysDeleteChildObjects(OBJSYS *pSys)
348 {
349 int i;
350
351 osRmCapUnregister(&pSys->pOsRmCaps);
352
353 for (i = NV_ARRAY_ELEMENTS(sysChildObjects) - 1; i >= 0; i--)
354 {
355 NvLength offset = sysChildObjects[i].childOffset;
356 Dynamic **ppChild = reinterpretCast(reinterpretCast(pSys, NvU8*) + offset, Dynamic**);
357 objDelete(*ppChild);
358 *ppChild = NULL;
359 }
360 }
361
362 static void
_sysRegistryOverrideResourceServer(OBJSYS * pSys,OBJGPU * pGpu)363 _sysRegistryOverrideResourceServer
364 (
365 OBJSYS *pSys,
366 OBJGPU *pGpu
367 )
368 {
369 NvU32 data32;
370
371 // Set read-only API lock override
372 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_READONLY_API_LOCK,
373 &data32) == NV_OK)
374 {
375 NvU32 apiMask = 0;
376
377 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _ALLOC_RESOURCE, _ENABLE, data32))
378 apiMask |= NVBIT(RS_API_ALLOC_RESOURCE);
379
380 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _FREE_RESOURCE, _ENABLE, data32))
381 apiMask |= NVBIT(RS_API_FREE_RESOURCE);
382
383 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _MAP, _ENABLE, data32))
384 apiMask |= NVBIT(RS_API_MAP);
385
386 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _UNMAP, _ENABLE, data32))
387 apiMask |= NVBIT(RS_API_UNMAP);
388
389 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _INTER_MAP, _ENABLE, data32))
390 apiMask |= NVBIT(RS_API_INTER_MAP);
391
392 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _INTER_UNMAP, _ENABLE, data32))
393 apiMask |= NVBIT(RS_API_INTER_UNMAP);
394
395 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _CTRL, _ENABLE, data32))
396 apiMask |= NVBIT(RS_API_CTRL);
397
398 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _COPY, _ENABLE, data32))
399 apiMask |= NVBIT(RS_API_COPY);
400
401 if (FLD_TEST_DRF(_REG_STR_RM, _READONLY_API_LOCK, _SHARE, _ENABLE, data32))
402 apiMask |= NVBIT(RS_API_SHARE);
403
404 pSys->apiLockMask = apiMask;
405 }
406 else
407 {
408 pSys->apiLockMask = NVBIT(RS_API_CTRL);
409 }
410
411 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_READONLY_API_LOCK_MODULE,
412 &data32) == NV_OK)
413 {
414 pSys->apiLockModuleMask = data32;
415 }
416 else
417 {
418 pSys->apiLockModuleMask = RM_LOCK_MODULE_GRP(RM_LOCK_MODULES_CLIENT);
419 }
420
421 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_CLIENT_HANDLE_LOOKUP,
422 &data32) == NV_OK)
423 {
424 pSys->setProperty(pSys, PDB_PROP_SYS_CLIENT_HANDLE_LOOKUP, !!data32);
425 }
426
427 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_LOCK_TIME_COLLECT,
428 &data32) == NV_OK)
429 {
430 pSys->setProperty(pSys, PDB_PROP_SYS_RM_LOCK_TIME_COLLECT, !!data32);
431 }
432
433 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_CLIENT_LIST_DEFERRED_FREE,
434 &data32) == NV_OK)
435 {
436 pSys->bUseDeferredClientListFree = !!data32;
437 }
438
439 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_CLIENT_LIST_DEFERRED_FREE_LIMIT,
440 &data32) == NV_OK)
441 {
442 pSys->clientListDeferredFreeLimit = data32;
443 }
444 }
445
446 static void
_sysRegistryOverrideExternalFabricMgmt(OBJSYS * pSys,OBJGPU * pGpu)447 _sysRegistryOverrideExternalFabricMgmt
448 (
449 OBJSYS *pSys,
450 OBJGPU *pGpu
451 )
452 {
453 NvU32 data32;
454
455 // Set external fabric management property
456 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_EXTERNAL_FABRIC_MGMT,
457 &data32) == NV_OK)
458 {
459 if (FLD_TEST_DRF(_REG_STR_RM, _EXTERNAL_FABRIC_MGMT, _MODE, _ENABLE, data32))
460 {
461 NV_PRINTF(LEVEL_INFO,
462 "Enabling external fabric management.\n");
463
464 pSys->setProperty(pSys, PDB_PROP_SYS_FABRIC_IS_EXTERNALLY_MANAGED, NV_TRUE);
465 }
466
467 if (FLD_TEST_DRF(_REG_STR_RM, _EXTERNAL_FABRIC_MGMT, _MODE, _DISABLE, data32))
468 {
469 NV_PRINTF(LEVEL_INFO,
470 "Disabling external fabric management.\n");
471
472 pSys->setProperty(pSys, PDB_PROP_SYS_FABRIC_IS_EXTERNALLY_MANAGED, NV_FALSE);
473 }
474 }
475 }
476
477 void
sysEnableExternalFabricMgmt_IMPL(OBJSYS * pSys)478 sysEnableExternalFabricMgmt_IMPL
479 (
480 OBJSYS *pSys
481 )
482 {
483 pSys->setProperty(pSys, PDB_PROP_SYS_FABRIC_IS_EXTERNALLY_MANAGED, NV_TRUE);
484
485 NV_PRINTF(LEVEL_INFO,
486 "Enabling external fabric management for Proxy NvSwitch systems.\n");
487 }
488
489 void
sysForceInitFabricManagerState_IMPL(OBJSYS * pSys)490 sysForceInitFabricManagerState_IMPL
491 (
492 OBJSYS *pSys
493 )
494 {
495 //
496 // We should only allow force init if there is not way to run fabric
497 // manager. For example, HGX-2 virtualization use-case.
498 //
499 if (pSys->getProperty(pSys, PDB_PROP_SYS_NVSWITCH_IS_PRESENT) ||
500 pSys->getProperty(pSys, PDB_PROP_SYS_FABRIC_MANAGER_IS_REGISTERED))
501 {
502 NV_ASSERT(0);
503 return;
504 }
505
506 pSys->setProperty(pSys, PDB_PROP_SYS_FABRIC_MANAGER_IS_INITIALIZED, NV_TRUE);
507
508 NV_PRINTF(LEVEL_INFO,
509 "Forcing fabric manager's state as initialized to unblock clients.\n");
510 }
511
512 static void
_sysNvSwitchDetection(OBJSYS * pSys)513 _sysNvSwitchDetection
514 (
515 OBJSYS *pSys
516 )
517 {
518
519 if (osIsNvswitchPresent())
520 {
521 pSys->setProperty(pSys, PDB_PROP_SYS_NVSWITCH_IS_PRESENT, NV_TRUE);
522
523 NV_PRINTF(LEVEL_INFO, "NvSwitch is found in the system\n");
524
525 sysEnableExternalFabricMgmt(pSys);
526 }
527 }
528
529 /*!
530 * @brief Initialize static system configuration data.
531 *
532 * @param[in] pSys SYSTEM object pointer
533 */
534 static void
_sysInitStaticConfig(OBJSYS * pSys)535 _sysInitStaticConfig(OBJSYS *pSys)
536 {
537 portMemSet(&pSys->staticConfig, 0, sizeof(pSys->staticConfig));
538 osInitSystemStaticConfig(&pSys->staticConfig);
539 }
540
541 NV_STATUS
coreInitializeRm(void)542 coreInitializeRm(void)
543 {
544 NV_STATUS status;
545 OBJSYS *pSys = NULL;
546
547 //
548 // Initialize libraries used by RM
549 //
550
551 // Portable runtime init
552 status = portInitialize();
553 if (status != NV_OK)
554 return status;
555
556 // Required before any NvLog (NV_PRINTF) calls
557 NVLOG_INIT(NULL);
558
559 // Required before any NV_PRINTF() calls
560 if (!DBG_INIT())
561 {
562 status = NV_ERR_GENERIC;
563 return status;
564 }
565
566 //
567 // Initialize OBJSYS which spawns all the RM internal modules
568 //
569 status = objCreate(&pSys, NVOC_NULL_OBJECT, OBJSYS);
570
571 nvAssertInit();
572
573 return status;
574 }
575
576 void
coreShutdownRm(void)577 coreShutdownRm(void)
578 {
579 OBJSYS *pSys = SYS_GET_INSTANCE();
580
581 //
582 // Destruct OBJSYS which frees all the RM internal modules
583 //
584 objDelete(pSys);
585
586 //
587 // Deinitialize libraries used by RM
588 //
589 nvAssertDestroy();
590
591 DBG_DESTROY();
592
593 NVLOG_DESTROY();
594
595 portShutdown();
596 }
597
598 // Obsolete RM init function -- code should migrate to new interfaces
599 NvS32
RmInitRm(void)600 RmInitRm(void)
601 {
602 return (coreInitializeRm() == NV_OK);
603 }
604
605 // Obsolete RM destroy function -- code should migrate to new interfaces
606 NvS32
RmDestroyRm(void)607 RmDestroyRm(void)
608 {
609 coreShutdownRm();
610 return NV_TRUE;
611 }
612
613 static NV_STATUS
_sysCreateOs(OBJSYS * pSys)614 _sysCreateOs(OBJSYS *pSys)
615 {
616 OBJOS *pOS;
617 NV_STATUS status;
618
619 // RMCONFIG: only if OS is enabled :-)
620 RMCFG_MODULE_ENABLED_OR_BAIL(OS);
621
622 status = objCreate(&pOS, pSys, OBJOS);
623 if (status != NV_OK)
624 {
625 return status;
626 }
627
628 status = constructObjOS(pOS);
629 if (status != NV_OK)
630 {
631 objDelete(pOS);
632 return status;
633 }
634
635 status = osRmCapRegisterSys(&pSys->pOsRmCaps);
636 if (status != NV_OK)
637 {
638 //
639 // Device objects needed for some access rights failed
640 // This is not system-critical since access rights are currently disabled,
641 // so continue booting, just log error.
642 //
643 // RS-TODO make this fail once RM Capabilities are enabled (Bug 2549938)
644 //
645 NV_PRINTF(LEVEL_ERROR, "RM Access Sys Cap creation failed: 0x%x\n", status);
646 }
647
648 pSys->pOS = pOS;
649
650 return NV_OK;
651 }
652
653 NV_STATUS
sysCaptureState_IMPL(OBJSYS * pSys)654 sysCaptureState_IMPL(OBJSYS *pSys)
655 {
656 return NV_OK;
657 }
658
659 OBJOS*
sysGetOs_IMPL(OBJSYS * pSys)660 sysGetOs_IMPL(OBJSYS *pSys)
661 {
662 if (pSys->pOS)
663 return pSys->pOS;
664
665 //
666 // A special case for any early 'get-object' calls for the OS
667 // object before there is an OS object. Some RC code called on
668 // DBG_BREAKPOINT assumes an OS object exists, and can cause a crash.
669 //
670 PORT_BREAKPOINT_ALWAYS();
671
672 return NULL;
673 }
674
675 void
sysInitRegistryOverrides_IMPL(OBJSYS * pSys)676 sysInitRegistryOverrides_IMPL
677 (
678 OBJSYS *pSys
679 )
680 {
681 OBJGPU *pGpu = NULL;
682 NvU32 data32 = 0;
683
684 if (pSys->getProperty(pSys,
685 PDB_PROP_SYS_REGISTRY_OVERRIDES_INITIALIZED))
686 {
687 // The registry overrides, if any, have already been applied.
688 return;
689 }
690
691 // Get some GPU - as of now we need some gpu to read registry.
692 pGpu = gpumgrGetSomeGpu();
693 if (pGpu == NULL)
694 {
695 // Too early call ! we can not read the registry.
696 return;
697 }
698
699 if ((osReadRegistryDword(pGpu,
700 NV_REG_STR_RM_ENABLE_EVENT_TRACER, &data32) == NV_OK) && data32 )
701 {
702 RMTRACE_ENABLE(data32);
703 }
704
705 if (osReadRegistryDword(pGpu,
706 NV_REG_STR_RM_CLIENT_DATA_VALIDATION, &data32) == NV_OK)
707 {
708 if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _KERNEL_BUFFERS, _ENABLED, data32))
709 {
710 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_KERNEL_BUFFERS, NV_TRUE);
711 }
712 else if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _KERNEL_BUFFERS, _DISABLED, data32))
713 {
714 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_KERNEL_BUFFERS, NV_FALSE);
715 }
716
717 if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _HANDLE, _ENABLED, data32))
718 {
719 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE, NV_TRUE);
720 }
721 else if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _HANDLE, _DISABLED, data32))
722 {
723 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE, NV_FALSE);
724 }
725
726 if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _STRICT_CLIENT, _ENABLED, data32))
727 {
728 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE_STRICT, NV_TRUE);
729 }
730 else if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _STRICT_CLIENT, _DISABLED, data32))
731 {
732 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE_STRICT, NV_FALSE);
733 }
734
735 if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _ALL, _ENABLED, data32))
736 {
737 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE, NV_TRUE);
738 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_KERNEL_BUFFERS, NV_TRUE);
739 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE_STRICT, NV_TRUE);
740 }
741 else if (FLD_TEST_DRF(_REG_STR_RM, _CLIENT_DATA_VALIDATION, _ALL, _DISABLED, data32))
742 {
743 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE, NV_FALSE);
744 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_KERNEL_BUFFERS, NV_FALSE);
745 pSys->setProperty(pSys, PDB_PROP_SYS_VALIDATE_CLIENT_HANDLE_STRICT, NV_FALSE);
746 }
747 }
748
749 pSys->setProperty(pSys, PDB_PROP_SYS_REGISTRY_OVERRIDES_INITIALIZED, NV_TRUE);
750
751 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_STREAM_MEMOPS,
752 &data32) == NV_OK)
753 {
754 if (FLD_TEST_DRF(_REG_STR_RM, _STREAM_MEMOPS, _ENABLE, _YES, data32))
755 {
756 pSys->setProperty(pSys, PDB_PROP_SYS_ENABLE_STREAM_MEMOPS, NV_TRUE);
757 }
758 }
759
760 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_PRIORITY_BOOST,
761 &data32) == NV_OK)
762 {
763 if (data32 == NV_REG_STR_RM_PRIORITY_BOOST_DISABLE)
764 pSys->setProperty(pSys, PDB_PROP_SYS_PRIORITY_BOOST, NV_FALSE);
765 else
766 pSys->setProperty(pSys, PDB_PROP_SYS_PRIORITY_BOOST, NV_TRUE);
767 }
768
769 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_PRIORITY_THROTTLE_DELAY,
770 &data32) == NV_OK)
771 {
772 pSys->setProperty(pSys, PDB_PROP_SYS_PRIORITY_THROTTLE_DELAY_US, data32);
773 }
774
775 _sysRegistryOverrideExternalFabricMgmt(pSys, pGpu);
776 _sysRegistryOverrideResourceServer(pSys, pGpu);
777
778 if (osBugCheckOnTimeoutEnabled())
779 {
780 pSys->setProperty(pSys, PDB_PROP_SYS_BUGCHECK_ON_TIMEOUT, NV_TRUE);
781 }
782
783 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_ENABLE_ROUTE_TO_PHYSICAL_LOCK_BYPASS,
784 &data32) == NV_OK)
785 {
786 pSys->setProperty(pSys, PDB_PROP_SYS_ROUTE_TO_PHYSICAL_LOCK_BYPASS, !!data32);
787 }
788
789 if (osReadRegistryDword(pGpu, NV_REG_STR_RM_GPU_LOCK_MIDPATH, &data32) == NV_OK)
790 {
791 pSys->setProperty(pSys, PDB_PROP_SYS_GPU_LOCK_MIDPATH_ENABLED, !!data32);
792 }
793
794 gpumgrSetGpuNvlinkBwModeFromRegistry(pGpu);
795 }
796
797 void
sysApplyLockingPolicy_IMPL(OBJSYS * pSys)798 sysApplyLockingPolicy_IMPL(OBJSYS *pSys)
799 {
800 g_resServ.bRouteToPhysicalLockBypass = pSys->getProperty(pSys, PDB_PROP_SYS_ROUTE_TO_PHYSICAL_LOCK_BYPASS);
801 g_resServ.roTopLockApiMask = pSys->apiLockMask;
802 }
803
804 NV_STATUS
sysSyncExternalFabricMgmtWAR_IMPL(OBJSYS * pSys,OBJGPU * pGpu)805 sysSyncExternalFabricMgmtWAR_IMPL
806 (
807 OBJSYS *pSys,
808 OBJGPU *pGpu
809 )
810 {
811 NV0000_CTRL_CMD_SYSTEM_SYNC_EXTERNAL_FABRIC_MGMT_PARAMS params;
812 RM_API *pRmApi = GPU_GET_PHYSICAL_RMAPI(pGpu);
813 NV_STATUS status = NV_OK;
814
815 params.bExternalFabricMgmt = pSys->getProperty(pSys,
816 PDB_PROP_SYS_FABRIC_IS_EXTERNALLY_MANAGED);
817
818 status = pRmApi->Control(pRmApi, pGpu->hInternalClient, pGpu->hInternalClient,
819 NV0000_CTRL_CMD_SYSTEM_SYNC_EXTERNAL_FABRIC_MGMT,
820 ¶ms, sizeof(params));
821
822 return status;
823 }
824