diff --git a/include/libcamera/base/utils.h b/include/libcamera/base/utils.h
index 0b7407f77..6ce1ace43 100644
--- a/include/libcamera/base/utils.h
+++ b/include/libcamera/base/utils.h
@@ -426,9 +426,7 @@ scope_exit(EF) -> scope_exit<EF>;
 } /* namespace utils */
 
 #ifndef __DOXYGEN__
-template<class CharT, class Traits>
-std::basic_ostream<CharT, Traits> &operator<<(std::basic_ostream<CharT, Traits> &os,
-					      const utils::Duration &d);
+std::ostream &operator<<(std::ostream &os, const utils::Duration &d);
 #endif
 
 } /* namespace libcamera */
diff --git a/src/libcamera/base/utils.cpp b/src/libcamera/base/utils.cpp
index 65d9181c9..2c3f2b7e6 100644
--- a/src/libcamera/base/utils.cpp
+++ b/src/libcamera/base/utils.cpp
@@ -658,11 +658,9 @@ void ScopeExitActions::release()
 } /* namespace utils */
 
 #ifndef __DOXYGEN__
-template<class CharT, class Traits>
-std::basic_ostream<CharT, Traits> &operator<<(std::basic_ostream<CharT, Traits> &os,
-					      const utils::Duration &d)
+std::ostream &operator<<(std::ostream &os, const utils::Duration &d)
 {
-	std::basic_ostringstream<CharT, Traits> s;
+	std::ostringstream s;
 
 	s.flags(os.flags());
 	s.imbue(os.getloc());
@@ -671,11 +669,6 @@ std::basic_ostream<CharT, Traits> &operator<<(std::basic_ostream<CharT, Traits>
 	s << d.get<std::micro>() << "us";
 	return os << s.str();
 }
-
-template
-std::basic_ostream<char, std::char_traits<char>> &
-operator<< <char, std::char_traits<char>>(std::basic_ostream<char, std::char_traits<char>> &os,
-					  const utils::Duration &d);
 #endif
 
 } /* namespace libcamera */
