     /// The end time of the span.
     public private(set) var endTime: Date?
     /// True if the span is ended.
-    private var endAtomic = ManagedAtomic<Bool>(false)
-    public private(set) var hasEnded: Bool {
-        set {
-            self.endAtomic.store(newValue, ordering: .relaxed)
-        }
+    fileprivate var endAtomic = ManagedAtomic<Bool>(false)
+    public var hasEnded: Bool {
         get {
             return self.endAtomic.load(ordering: .relaxed)
         }

    }

    private func addEvent(event: SpanData.Event) {
        if hasEnded {
            return
        }
        eventsSyncLock.withLockVoid {
            events.append(event)
            totalRecordedEvents += 1
        }

    }

    public func end(time: Date) {
        if endAtomic.exchange(true, ordering: .relaxed) {
            return
        }
        eventsSyncLock.withLockVoid{
            attributesSyncLock.withLockVoid{
                isRecording = false
            }
        }
        endTime = time
        spanProcessor.onEnd(span: self)
        scope?.close()
    }

