Safe Dispose of Timer
Review


property Interval and methods ExternalStart, ExternalStart should throw ObjectDisposedException if _isDisposing is true
property Interval and methods ExternalStart, ExternalStart should also acquire a lock on _syncObject
when implementing the dispose pattern make sure to include a destructor ~DisposableSafeTimer or seal your class
_isDisposing should be renamed to _disposed
when disposing, you should also clean your event listeners Elapsed = null to avoid a memory leak
do you really want to put Elapsed?.Invoke(sender, e); inside the lock? Think about possible race conditions or other side effects. What if a registered listener calls Dispose in the listener?
check out different suggestions to reset the timer. Yours is fine though.
a tiny enhancement might be to create the lock only when it is null using Interlocked.CompareExchange, instead of immediately creating an instance.