{"record":{"id":"1f319cfd1721883b","repo":"dotnet/reactive","slug":"value-cannot-be-null-parameter-disposable-refcountdisposable","errorCode":null,"errorMessage":"Value cannot be null. (Parameter 'disposable')","messagePattern":"Value cannot be null\\. \\(Parameter 'disposable'\\)","errorType":"exception","errorClass":"ArgumentNullException","httpStatus":null,"severity":"error","filePath":"Rx.NET/Source/src/System.Reactive/Disposables/RefCountDisposable.cs","lineNumber":42,"sourceCode":"\n        /// <summary>\n        /// Initializes a new instance of the <see cref=\"RefCountDisposable\"/> class with the specified disposable.\n        /// </summary>\n        /// <param name=\"disposable\">Underlying disposable.</param>\n        /// <exception cref=\"ArgumentNullException\"><paramref name=\"disposable\"/> is null.</exception>\n        public RefCountDisposable(IDisposable disposable) : this(disposable, false)\n        {\n        }\n\n        /// <summary>\n        /// Initializes a new instance of the <see cref=\"RefCountDisposable\"/> class with the specified disposable.\n        /// </summary>\n        /// <param name=\"disposable\">Underlying disposable.</param>\n        /// <param name=\"throwWhenDisposed\">Indicates whether subsequent calls to <see cref=\"GetDisposable\"/> should throw when this instance is disposed.</param>\n        /// <exception cref=\"ArgumentNullException\"><paramref name=\"disposable\"/> is null.</exception>\n        public RefCountDisposable(IDisposable disposable, bool throwWhenDisposed)\n        {\n            _disposable = disposable ?? throw new ArgumentNullException(nameof(disposable));\n            _count = 0;\n            _throwWhenDisposed = throwWhenDisposed;\n        }\n\n        /// <summary>\n        /// Gets a value that indicates whether the object is disposed.\n        /// </summary>\n        public bool IsDisposed => Volatile.Read(ref _count) == int.MinValue;\n\n        /// <summary>\n        /// Returns a dependent disposable that when disposed decreases the refcount on the underlying disposable.\n        /// </summary>\n        /// <returns>A dependent disposable contributing to the reference count that manages the underlying disposable's lifetime.</returns>\n        /// <exception cref=\"ObjectDisposedException\">This instance has been disposed and is configured to throw in this case by <see cref=\"RefCountDisposable(IDisposable, bool)\"/>.</exception>\n        public IDisposable GetDisposable()\n        {\n            // the current state\n            var cnt = Volatile.Read(ref _count);","sourceCodeStart":24,"sourceCodeEnd":60,"githubUrl":"https://github.com/dotnet/reactive/blob/94b5d5ab912789f5abe9a72138a25bbd716fe59c/Rx.NET/Source/src/System.Reactive/Disposables/RefCountDisposable.cs#L24-L60","documentation":"The RefCountDisposable constructor requires a non-null underlying IDisposable; System.Reactive explicitly guards it with a null check and throws ArgumentNullException. The reference-counting wrapper cannot function without a disposable to ref-count, so a null argument is treated as a programming error rather than silently tolerated.","triggerScenarios":"Calling new RefCountDisposable(null) or new RefCountDisposable(null, throwWhenDisposed) — i.e. passing a null IDisposable as the 'disposable' parameter, typically when a lazy/deferred producer of the underlying disposable returned null.","commonSituations":"Passing the result of a factory method or dictionary lookup that returned null (e.g. GetDisposable() from another container), conditional initialization where the inner disposable was never created, or refactoring that changed the order of assignment to a backing field.","solutions":["Ensure the underlying IDisposable is created before constructing the RefCountDisposable.","Use Disposable.Empty as an explicit non-null placeholder when there is nothing to dispose.","Guard with a null check and fall back to Disposable.Empty or skip creating the RefCountDisposable entirely."],"exampleFix":"// before\nvar refCount = new RefCountDisposable(GetInner()); // GetInner() may return null\n// after\nvar inner = GetInner() ?? Disposable.Empty;\nvar refCount = new RefCountDisposable(inner);","handlingStrategy":"validation","validationCode":"if (inner is null) throw new InvalidOperationException(\"Underlying disposable must be created before RefCountDisposable\");\nvar rc = new RefCountDisposable(inner);","typeGuard":"static bool IsUsable(IDisposable d) => d is not null;","tryCatchPattern":"try { var rc = new RefCountDisposable(inner); }\ncatch (ArgumentNullException ex) when (ex.ParamName == \"disposable\") { /* fall back to Disposable.Empty semantics */ }","preventionTips":["Never pass factory results that can return null directly into the constructor; coalesce with Disposable.Empty.","Treat null IDisposable as a bug; enforce non-null via nullable reference types (IDisposable not null?).","Add unit tests covering resource acquisition failure paths."],"tags":["null-argument","disposables","system-reactive","argument-validation"],"backgroundTag":"null-argument","analyzedSha":"94b5d5ab912789f5abe9a72138a25bbd716fe59c","analyzedAt":"2026-09-15T02:26:24.759Z","contentChangedAt":"2026-09-15T02:26:24.759Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}