From 14903ca18df3a0c327ae1794025e58c91bc7f802 Mon Sep 17 00:00:00 2001 From: Andrew Bettison Date: Tue, 24 Apr 2018 00:06:00 +0930 Subject: [PATCH] Add log outputter for Apple iOS and macOS On iOS, the log outputter uses Apple's Unified Logging System, but on Mac OS, the logger uses the older Syslog API so that it will compile on platforms older than macOS 10.13 High Sierra. --- Makefile.in | 15 ++-- servaldswift.swift | 17 +---- swift-client-api/Makefile.in | 8 +-- swift-daemon-api/Sources/log.swift | 19 +++++ swift-daemon-api/Sources/log_output.swift | 85 +++++++++++++++++++++++ 5 files changed, 116 insertions(+), 28 deletions(-) create mode 100644 swift-daemon-api/Sources/log_output.swift diff --git a/Makefile.in b/Makefile.in index ad846ad8..1d43e10e 100644 --- a/Makefile.in +++ b/Makefile.in @@ -1,5 +1,4 @@ # Makefile.in for Serval DNA daemon and libraries -# nnnn # vim: noet ts=8 sts=0 sw=8 prefix=@prefix@ exec_prefix=@exec_prefix@ @@ -21,7 +20,7 @@ SWIFTCFLAGS= @SWIFTCFLAGS@ -I$(abs_builddir) -I$(abs_srcdir) SWIFTLIBS= @LIBS@ SWIFT_BUILD= @SWIFT_BUILD@ -SWIFT_BUILD_FLAGS= $(addprefix -Xswiftc , $(SWIFTCFLAGS)) +SWIFT_BUILD_FLAGS= $(addprefix -Xswiftc , $(SWIFTCFLAGS)) SWIFT_MODULE_NAME= ServalDNA SWIFT_PACKAGE_DIR= $(srcdir)/swift-daemon-api @@ -182,9 +181,10 @@ test: servaldswift clean: swift-daemon-api-clean swift-client-api-clean -.PHONY: swift-daemon-api swift-daemon-api-clean swift-client-api swift-client-api-clean +.PHONY: swift-daemon-api swift-daemon-api-clean \ + swift-client-api swift-client-api-clean -libServalDNA.a $(SWIFT_MODULE_NAME).swiftmodule $(SWIFT_MODULE_NAME).swiftdoc: swift-daemon-api +lib$(SWIFT_MODULE_NAME).a $(SWIFT_MODULE_NAME).swiftmodule $(SWIFT_MODULE_NAME).swiftdoc: swift-daemon-api cp $(SWIFT_BUILD_DIR)/debug/$(notdir $@) $@ swift-daemon-api: @@ -198,11 +198,10 @@ swift-daemon-api-clean: $(SWIFT_MODULE_NAME).swiftdoc swift-client-api: - @mkdir -p swift-client-api - cd swift-client-api && $(MAKE) all + cd $@ && $(MAKE) all swift-client-api-clean: - cd swift-client-api 2>/dev/null && $(MAKE) clean + cd $(@:-clean=) 2>/dev/null && $(MAKE) clean endif # $(SWIFTC) @@ -393,7 +392,7 @@ ifneq ($(SWIFTC),) # Only provide Swift targets if the Swift compiler is availab servaldswift: $(srcdir)/servaldswift.swift \ $(OBJSDIR_SERVALD)/servald_features.o \ $(SWIFT_MODULE_NAME).swiftmodule \ - libServalDNA.a \ + lib$(SWIFT_MODULE_NAME).a \ libservaldaemon.a @echo SWIFT $@ @$(SWIFTC) -emit-executable -o $@ \ diff --git a/servaldswift.swift b/servaldswift.swift index a8c51e5b..c91bb259 100644 --- a/servaldswift.swift +++ b/servaldswift.swift @@ -19,25 +19,10 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. import Foundation import ServalDNA -import servald.log // Logging -// -// A simplistic console log outputter that writes to standard error and is not -// configurable. Note that log_output_console.o is not linked into -// servaldswift, in order to avoid duplicate log outputs on standard error. -private func logPrint(_ level: CInt, _ message: UnsafePointer?, _ overrun: Int8) { - let level_text = String(cString: serval_log_level_prefix_string(level)!) - let message_text = String(cString: message!) - FileHandle.standardError.write("\(level_text) \(message_text)\n".data(using:.utf8)!) -} - -serval_log_delegate.print = logPrint -serval_log_delegate.minimum_level = LOG_LEVEL_WARN -serval_log_delegate.show_prolog = 1 -serval_log_delegate.show_pid = 1 -serval_log_delegate.show_time = 1 +logSetup() // Output diff --git a/swift-client-api/Makefile.in b/swift-client-api/Makefile.in index 69d7a4eb..4292f26a 100644 --- a/swift-client-api/Makefile.in +++ b/swift-client-api/Makefile.in @@ -1,4 +1,4 @@ -# Makefile.in for Serval DNA Swift API +# Makefile.in for Serval DNA Swift Client API # vim: noet ts=8 sts=0 sw=8 prefix=@prefix@ exec_prefix=@exec_prefix@ @@ -18,7 +18,7 @@ SWIFTCFLAGS= @SWIFTCFLAGS@ SWIFTCFLAGS+= -I $(srcdir) SWIFT_BUILD= @SWIFT_BUILD@ -SWIFT_BUILD_FLAGS= $(addprefix -Xswiftc , $(SWIFTCFLAGS)) +SWIFT_BUILD_FLAGS= $(addprefix -Xswiftc , $(SWIFTCFLAGS)) DEFS= @DEFS@ SWIFTDEFS= $(addprefix -Xcc , $(DEFS)) @@ -48,9 +48,9 @@ package: cd $(SWIFT_PACKAGE_DIR) && \ $(SWIFT_BUILD) --build-path $(SWIFT_BUILD_DIR) $(SWIFT_BUILD_FLAGS) $(SWIFTDEFS) -$(SWIFT_BUILD_DIR)/debug/libServalClient.a: package +$(SWIFT_BUILD_DIR)/debug/lib$(SWIFT_MODULE_NAME).a: package -swift-client-util: $(srcdir)/client_util.swift $(SWIFT_BUILD_DIR)/debug/libServalClient.a +swift-client-util: $(srcdir)/client_util.swift $(SWIFT_BUILD_DIR)/debug/lib$(SWIFT_MODULE_NAME).a @echo SWIFT $@ @$(SWIFTC) -emit-executable $(SWIFTCFLAGS) $(SWIFTDEFS) -I $(SWIFT_BUILD_DIR)/debug -o $@ $^ diff --git a/swift-daemon-api/Sources/log.swift b/swift-daemon-api/Sources/log.swift index ee0765b9..547c8c6d 100644 --- a/swift-daemon-api/Sources/log.swift +++ b/swift-daemon-api/Sources/log.swift @@ -1,3 +1,22 @@ +/* +Serval DNA support - Swift entry points to Serval logging operations +Copyright 2017 Flinders University + +This program is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation; either version 2 +of the License, or (at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + import servald.log private func serval_log(level: CInt, format: String, va_list: CVaListPointer) { diff --git a/swift-daemon-api/Sources/log_output.swift b/swift-daemon-api/Sources/log_output.swift new file mode 100644 index 00000000..c13f8e25 --- /dev/null +++ b/swift-daemon-api/Sources/log_output.swift @@ -0,0 +1,85 @@ +/* +Serval DNA support - log outputter for iOS (unified logging) +Copyright 2018 Flinders University + +This program is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation; either version 2 +of the License, or (at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +*/ + +import Foundation +import servald.log + +#if os(iOS) + +import os + +// A Serval log outputter that uses Apple's unified logging system (introduced +// in iOS 10.0 and macOS 10.12 "Sierra") + +private func logPrint(_ level: CInt, _ message: UnsafePointer?, _ overrun: Int8) { + let level_text = String(cString: serval_log_level_prefix_string(level)!) + let message_text = String(cString: message!) + let log_type : OSLogType + switch level { + case LOG_LEVEL_DEBUG: log_type = OSLogType.debug + case LOG_LEVEL_INFO: log_type = OSLogType.info + case LOG_LEVEL_HINT: log_type = OSLogType.info + case LOG_LEVEL_WARN: log_type = OSLogType.default + case LOG_LEVEL_ERROR: log_type = OSLogType.error + case LOG_LEVEL_FATAL: log_type = OSLogType.fault + default: return + } + os_log("%@ %@", type: log_type, level_text, message_text) +} + +#elseif os(macOS) + +// A Serval log outputter that uses Apple's (legacy) System Log facility. + +private func logPrint(_ level: CInt, _ message: UnsafePointer?, _ overrun: Int8) { + let level_text = String(cString: serval_log_level_prefix_string(level)!) + let message_text = String(cString: message!) + NSLog("%s %s", level_text, message_text) +} + +#else + +// A Serval log outputter that writes to standard error and is not +// configurable. Warning: If you also link log_output_console.o into the +// executable, you will get duplicate log outputs on standard error. + +private func logPrint(_ level: CInt, _ message: UnsafePointer?, _ overrun: Int8) { + let level_text = String(cString: serval_log_level_prefix_string(level)!) + let message_text = String(cString: message!) + FileHandle.standardError.write("\(level_text) \(message_text)\n".data(using:.utf8)!) +} + +#endif + +public func logSetup() { + serval_log_delegate.print = logPrint + serval_log_delegate.minimum_level = LOG_LEVEL_DEBUG + serval_log_delegate.show_prolog = 1 +#if os(iOS) || os(macOS) + // Apple's unified logging system (iOS) and syslog (macOS) both record the + // timestamp and process ID in all log messages, so we don't need to. + serval_log_delegate.show_pid = 0 + serval_log_delegate.show_time = 0 +#else + // If logging to standard error, do prefix every message with the timestamp + // and process ID. + serval_log_delegate.show_pid = 1 + serval_log_delegate.show_time = 1 +#endif +}