Merge pull request #2721 from ludovic-henry/fix-mono_ms_ticks
authorLudovic Henry <ludovic@xamarin.com>
Mon, 25 Apr 2016 15:22:15 +0000 (11:22 -0400)
committerLudovic Henry <ludovic@xamarin.com>
Mon, 25 Apr 2016 15:22:15 +0000 (11:22 -0400)
[runtime] Fix potential overflow when using mono_msec_ticks

1083 files changed:
CONTRIBUTING.md
COPYING.LIB
LICENSE
PATENTS.TXT [new file with mode: 0644]
README.md
acceptance-tests/SUBMODULES.json
acceptance-tests/coreclr.mk
acceptance-tests/roslyn.mk
acceptance-tests/versions.py
configure.ac
docs/docs.make
external/android-libunwind/README [new file with mode: 0644]
external/android-libunwind/include/libunwind-aarch64.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-arm.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-common.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-coredump.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-dynamic.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-hppa.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-ia64.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-mips.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-ppc32.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-ppc64.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-ptrace.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-sh.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-x86.h [new file with mode: 0644]
external/android-libunwind/include/libunwind-x86_64.h [new file with mode: 0644]
external/android-libunwind/include/libunwind.h [new file with mode: 0644]
external/android-libunwind/include/unwind.h [new file with mode: 0644]
external/referencesource
libgc/configure.ac
man/mono.1
man/mprof-report.1
mcs/COPYING.LIB [deleted file]
mcs/LICENSE [deleted file]
mcs/LICENSE.CC [deleted file]
mcs/LICENSE.GPL [deleted file]
mcs/LICENSE.LGPL [deleted file]
mcs/LICENSE.MPL [deleted file]
mcs/LICENSE.MSPL [deleted file]
mcs/MIT.X11 [deleted file]
mcs/Makefile
mcs/README
mcs/build/Makefile
mcs/build/config-default.make
mcs/build/executable.make
mcs/build/gensources.sh
mcs/build/library.make
mcs/build/profiles/build.make
mcs/build/profiles/mobile.make
mcs/build/profiles/mobile_static.make
mcs/build/profiles/monodroid.make
mcs/build/profiles/monotouch_runtime.make
mcs/build/profiles/net_4_x.make
mcs/build/profiles/xammac.make
mcs/build/profiles/xbuild_12.make
mcs/build/profiles/xbuild_14.make
mcs/build/rules.make
mcs/build/tests.make
mcs/class/Accessibility/Makefile
mcs/class/Commons.Xml.Relaxng/Makefile
mcs/class/Compat.ICSharpCode.SharpZipLib/Makefile
mcs/class/Cscompmgd/Makefile
mcs/class/CustomMarshalers/Makefile
mcs/class/Facades/Makefile
mcs/class/Facades/Microsoft.Win32.Primitives/Makefile
mcs/class/Facades/Microsoft.Win32.Registry.AccessControl/Makefile
mcs/class/Facades/Microsoft.Win32.Registry/Makefile
mcs/class/Facades/System.AppContext/Makefile
mcs/class/Facades/System.Collections.Concurrent/Makefile
mcs/class/Facades/System.Collections.NonGeneric/Makefile
mcs/class/Facades/System.Collections.Specialized/Makefile
mcs/class/Facades/System.Collections/Makefile
mcs/class/Facades/System.ComponentModel.Annotations/Makefile
mcs/class/Facades/System.ComponentModel.EventBasedAsync/Makefile
mcs/class/Facades/System.ComponentModel.Primitives/Makefile
mcs/class/Facades/System.ComponentModel.TypeConverter/Makefile
mcs/class/Facades/System.ComponentModel/Makefile
mcs/class/Facades/System.Console/Makefile
mcs/class/Facades/System.Data.Common/Makefile
mcs/class/Facades/System.Data.SqlClient/Makefile
mcs/class/Facades/System.Diagnostics.Contracts/Makefile
mcs/class/Facades/System.Diagnostics.Debug/Makefile
mcs/class/Facades/System.Diagnostics.FileVersionInfo/Makefile
mcs/class/Facades/System.Diagnostics.PerformanceCounter/Makefile
mcs/class/Facades/System.Diagnostics.Process/Makefile
mcs/class/Facades/System.Diagnostics.StackTrace/Makefile
mcs/class/Facades/System.Diagnostics.TextWriterTraceListener/Makefile
mcs/class/Facades/System.Diagnostics.Tools/Makefile
mcs/class/Facades/System.Diagnostics.TraceEvent/Makefile
mcs/class/Facades/System.Diagnostics.TraceSource/Makefile
mcs/class/Facades/System.Diagnostics.Tracing/Makefile
mcs/class/Facades/System.Dynamic.Runtime/Makefile
mcs/class/Facades/System.Globalization.Calendars/Makefile
mcs/class/Facades/System.Globalization.Extensions/Makefile
mcs/class/Facades/System.Globalization/Makefile
mcs/class/Facades/System.IO.Compression.ZipFile/Makefile
mcs/class/Facades/System.IO.FileSystem.AccessControl/Makefile
mcs/class/Facades/System.IO.FileSystem.DriveInfo/Makefile
mcs/class/Facades/System.IO.FileSystem.Primitives/Makefile
mcs/class/Facades/System.IO.FileSystem.Watcher/Makefile
mcs/class/Facades/System.IO.FileSystem/Makefile
mcs/class/Facades/System.IO.IsolatedStorage/Makefile
mcs/class/Facades/System.IO.MemoryMappedFiles/Makefile
mcs/class/Facades/System.IO.Pipes/Makefile
mcs/class/Facades/System.IO.UnmanagedMemoryStream/Makefile
mcs/class/Facades/System.IO/Makefile
mcs/class/Facades/System.Linq.Expressions/Makefile
mcs/class/Facades/System.Linq.Parallel/Makefile
mcs/class/Facades/System.Linq.Queryable/Makefile
mcs/class/Facades/System.Linq/Makefile
mcs/class/Facades/System.Net.AuthenticationManager/Makefile
mcs/class/Facades/System.Net.Cache/Makefile
mcs/class/Facades/System.Net.Http.WebRequestHandler/Makefile
mcs/class/Facades/System.Net.HttpListener/Makefile
mcs/class/Facades/System.Net.Mail/Makefile
mcs/class/Facades/System.Net.NameResolution/Makefile
mcs/class/Facades/System.Net.NetworkInformation/Makefile
mcs/class/Facades/System.Net.Primitives/Makefile
mcs/class/Facades/System.Net.Requests/Makefile
mcs/class/Facades/System.Net.Security/Makefile
mcs/class/Facades/System.Net.ServicePoint/Makefile
mcs/class/Facades/System.Net.Sockets/Makefile
mcs/class/Facades/System.Net.Utilities/Makefile
mcs/class/Facades/System.Net.WebHeaderCollection/Makefile
mcs/class/Facades/System.Net.WebSockets.Client/Makefile
mcs/class/Facades/System.Net.WebSockets/Makefile
mcs/class/Facades/System.ObjectModel/Makefile
mcs/class/Facades/System.Private.CoreLib.InteropServices/Makefile
mcs/class/Facades/System.Private.CoreLib.Threading/Makefile
mcs/class/Facades/System.Reflection.Emit.ILGeneration/Makefile
mcs/class/Facades/System.Reflection.Emit.Lightweight/Makefile
mcs/class/Facades/System.Reflection.Emit/Makefile
mcs/class/Facades/System.Reflection.Extensions/Makefile
mcs/class/Facades/System.Reflection.Primitives/Makefile
mcs/class/Facades/System.Reflection.TypeExtensions/Makefile
mcs/class/Facades/System.Reflection/Makefile
mcs/class/Facades/System.Resources.ReaderWriter/Makefile
mcs/class/Facades/System.Resources.ResourceManager/Makefile
mcs/class/Facades/System.Runtime.CompilerServices.VisualC/Makefile
mcs/class/Facades/System.Runtime.Extensions/Makefile
mcs/class/Facades/System.Runtime.Handles/Makefile
mcs/class/Facades/System.Runtime.InteropServices.WindowsRuntime/Makefile
mcs/class/Facades/System.Runtime.InteropServices/Makefile
mcs/class/Facades/System.Runtime.Numerics/Makefile
mcs/class/Facades/System.Runtime.Serialization.Json/Makefile
mcs/class/Facades/System.Runtime.Serialization.Primitives/Makefile
mcs/class/Facades/System.Runtime.Serialization.Xml/Makefile
mcs/class/Facades/System.Runtime/Makefile
mcs/class/Facades/System.Security.AccessControl/Makefile
mcs/class/Facades/System.Security.Claims/Makefile
mcs/class/Facades/System.Security.Cryptography.DeriveBytes/Makefile
mcs/class/Facades/System.Security.Cryptography.Encoding/Makefile
mcs/class/Facades/System.Security.Cryptography.Encryption.Aes/Makefile
mcs/class/Facades/System.Security.Cryptography.Encryption.ECDiffieHellman/Makefile
mcs/class/Facades/System.Security.Cryptography.Encryption.ECDsa/Makefile
mcs/class/Facades/System.Security.Cryptography.Encryption/Makefile
mcs/class/Facades/System.Security.Cryptography.Hashing.Algorithms/Makefile
mcs/class/Facades/System.Security.Cryptography.Hashing/Makefile
mcs/class/Facades/System.Security.Cryptography.ProtectedData/Makefile
mcs/class/Facades/System.Security.Cryptography.RSA/Makefile
mcs/class/Facades/System.Security.Cryptography.RandomNumberGenerator/Makefile
mcs/class/Facades/System.Security.Cryptography.X509Certificates/Makefile
mcs/class/Facades/System.Security.Principal.Windows/Makefile
mcs/class/Facades/System.Security.Principal/Makefile
mcs/class/Facades/System.Security.SecureString/Makefile
mcs/class/Facades/System.ServiceModel.Duplex/Makefile
mcs/class/Facades/System.ServiceModel.Http/Makefile
mcs/class/Facades/System.ServiceModel.NetTcp/Makefile
mcs/class/Facades/System.ServiceModel.Primitives/Makefile
mcs/class/Facades/System.ServiceModel.Security/Makefile
mcs/class/Facades/System.ServiceProcess.ServiceController/Makefile
mcs/class/Facades/System.Text.Encoding.Extensions/Makefile
mcs/class/Facades/System.Text.Encoding/Makefile
mcs/class/Facades/System.Text.RegularExpressions/Makefile
mcs/class/Facades/System.Threading.AccessControl/Makefile
mcs/class/Facades/System.Threading.Overlapped/Makefile
mcs/class/Facades/System.Threading.Tasks.Parallel/Makefile
mcs/class/Facades/System.Threading.Tasks/Makefile
mcs/class/Facades/System.Threading.Thread/Makefile
mcs/class/Facades/System.Threading.ThreadPool/Makefile
mcs/class/Facades/System.Threading.Timer/Makefile
mcs/class/Facades/System.Threading/Makefile
mcs/class/Facades/System.Xml.ReaderWriter/Makefile
mcs/class/Facades/System.Xml.XDocument/Makefile
mcs/class/Facades/System.Xml.XPath.XDocument/Makefile
mcs/class/Facades/System.Xml.XPath/Makefile
mcs/class/Facades/System.Xml.XmlDocument/Makefile
mcs/class/Facades/System.Xml.XmlSerializer/Makefile
mcs/class/Facades/System.Xml.Xsl.Primitives/Makefile
mcs/class/I18N/CJK/ISO2022JP.cs
mcs/class/I18N/CJK/Makefile
mcs/class/I18N/CJK/Test/texts/japanese-50221.txt
mcs/class/I18N/CJK/Test/texts/japanese-50222.txt
mcs/class/I18N/CJK/Test/texts/japanese-51932.txt
mcs/class/I18N/CJK/Test/texts/japanese-932.txt
mcs/class/I18N/CJK/Test/texts/japanese-utf8.txt
mcs/class/I18N/Common/Makefile
mcs/class/I18N/MidEast/Makefile
mcs/class/I18N/Other/Makefile
mcs/class/I18N/Rare/Makefile
mcs/class/I18N/West/Makefile
mcs/class/IBM.Data.DB2/Makefile
mcs/class/ICSharpCode.SharpZipLib/Makefile
mcs/class/Makefile
mcs/class/Microsoft.Build.Engine/Makefile
mcs/class/Microsoft.Build.Framework/Makefile
mcs/class/Microsoft.Build.Tasks/Makefile
mcs/class/Microsoft.Build.Tasks/Microsoft.Build.Tasks/AssignProjectConfiguration.cs
mcs/class/Microsoft.Build.Tasks/Microsoft.Build.Tasks/CodeTaskFactory.cs
mcs/class/Microsoft.Build.Tasks/Test/Microsoft.Build.Tasks/AssignProjectConfigurationTest.cs
mcs/class/Microsoft.Build.Utilities/Makefile
mcs/class/Microsoft.Build/Makefile
mcs/class/Microsoft.Build/Microsoft.Build.Execution/BuildManager.cs
mcs/class/Microsoft.Build/Microsoft.Build.Execution/ProjectInstance.cs
mcs/class/Microsoft.Build/Microsoft.Build.Internal/BuildNodeManager.cs
mcs/class/Microsoft.VisualC/Makefile
mcs/class/MicrosoftAjaxLibrary/License.htm
mcs/class/Mono.C5/Makefile
mcs/class/Mono.C5/Test/AssemblyInfo.cs
mcs/class/Mono.CSharp/Makefile
mcs/class/Mono.Cecil.Mdb/Makefile
mcs/class/Mono.Cecil/Makefile
mcs/class/Mono.CodeContracts/Makefile
mcs/class/Mono.CompilerServices.SymbolWriter/Makefile
mcs/class/Mono.Data.Sqlite/Mono.Data.Sqlite_2.0/SQLiteConvert.cs
mcs/class/Mono.Data.Tds/Makefile
mcs/class/Mono.Debugger.Soft/Makefile
mcs/class/Mono.Directory.LDAP/Makefile
mcs/class/Mono.Dynamic.Interpreter/Makefile
mcs/class/Mono.Http/Makefile
mcs/class/Mono.Management/Makefile
mcs/class/Mono.Messaging.RabbitMQ/Makefile
mcs/class/Mono.Messaging/Makefile
mcs/class/Mono.Options/Makefile
mcs/class/Mono.Options/Mono.Options/Options.cs
mcs/class/Mono.Options/Test/Mono.Options/OptionSetTest.cs
mcs/class/Mono.Parallel/Makefile
mcs/class/Mono.Posix/Makefile
mcs/class/Mono.Security.Providers.NewTls/Makefile
mcs/class/Mono.Security/Assembly/AssemblyInfo.cs
mcs/class/Mono.Security/Makefile
mcs/class/Mono.Security/Mono.Security.Authenticode/AuthenticodeDeformatter.cs
mcs/class/Mono.Security/Mono.Security.Cryptography/MD2Managed.cs
mcs/class/Mono.Security/Mono.Security.Cryptography/MD4Managed.cs
mcs/class/Mono.Security/Mono.Security.Cryptography/SHA224Managed.cs
mcs/class/Mono.Security/Mono.Security.Interface/CertificateValidationHelper.cs
mcs/class/Mono.Security/Mono.Security.Interface/MonoTlsProvider.cs
mcs/class/Mono.Security/monotouch_Mono.Security.dll.sources
mcs/class/Mono.Security/monotouch_opt_Mono.Security.dll.sources [deleted file]
mcs/class/Mono.Security/monotouch_tv_opt_Mono.Security.dll.sources [deleted file]
mcs/class/Mono.Security/monotouch_watch_opt_Mono.Security.dll.sources [deleted file]
mcs/class/Mono.Security/xammac_Mono.Security.dll.sources
mcs/class/Mono.Security/xammac_opt_Mono.Security.dll.sources [deleted file]
mcs/class/Mono.Simd/Makefile
mcs/class/Mono.WebBrowser/tools/xpidl2cs/xpidl2cs.pl
mcs/class/Mono.XBuild.Tasks/Makefile
mcs/class/Mono.Xml.Ext/Makefile
mcs/class/Novell.Directory.Ldap/Makefile
mcs/class/PEAPI/Makefile
mcs/class/RabbitMQ.Client/Makefile.orig [deleted file]
mcs/class/RabbitMQ.Client/src/apigen/Makefile
mcs/class/System.Configuration.Install/Makefile
mcs/class/System.Configuration/Makefile
mcs/class/System.Configuration/System.Configuration/InternalConfigurationHost.cs
mcs/class/System.Configuration/Test/standalone/Makefile
mcs/class/System.Configuration/Test/standalone/t48.cs [new file with mode: 0644]
mcs/class/System.Configuration/Test/standalone/t48.exe.config [new file with mode: 0644]
mcs/class/System.Configuration/Test/standalone/t48.exe.expected [new file with mode: 0644]
mcs/class/System.Core/Makefile
mcs/class/System.Core/monotouch_tv_System.Core.dll.sources
mcs/class/System.Core/monotouch_watch_System.Core.dll.sources
mcs/class/System.Core/xammac_System.Core.dll.sources
mcs/class/System.Data.OracleClient/Makefile
mcs/class/System.Data.OracleClient/System.Data.OracleClient/OracleConnection.cs
mcs/class/System.Data.Services/Makefile
mcs/class/System.Data/Makefile
mcs/class/System.Deployment/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Deployment/Makefile [new file with mode: 0644]
mcs/class/System.Deployment/System.Deployment.dll.sources [new file with mode: 0644]
mcs/class/System.Design/Makefile
mcs/class/System.DirectoryServices/Makefile
mcs/class/System.Drawing.Design/Makefile
mcs/class/System.Drawing/Makefile
mcs/class/System.EnterpriseServices/Makefile
mcs/class/System.IO.Compression.FileSystem/Makefile
mcs/class/System.IO.Compression/Makefile
mcs/class/System.IdentityModel/Makefile
mcs/class/System.Management/Makefile
mcs/class/System.Messaging/Makefile
mcs/class/System.Net.Http.WebRequest/Makefile
mcs/class/System.Net.Http/CFContentStream.cs [new file with mode: 0644]
mcs/class/System.Net.Http/CFNetworkHandler.cs [new file with mode: 0644]
mcs/class/System.Net.Http/Documentation/en/index.xml
mcs/class/System.Net.Http/HttpClientEx.cs [new file with mode: 0644]
mcs/class/System.Net.Http/Makefile
mcs/class/System.Net.Http/System.Net.Http/HttpClient.android.cs [new file with mode: 0644]
mcs/class/System.Net.Http/System.Net.Http/HttpClient.mac.cs [new file with mode: 0644]
mcs/class/System.Net.Http/Test/System.Net.Http/HttpClientTest.cs
mcs/class/System.Net.Http/monodroid_System.Net.Http.dll.sources [new file with mode: 0644]
mcs/class/System.Net.Http/xammac_System.Net.Http.dll.sources
mcs/class/System.Net.Http/xammac_net_4_5_System.Net.Http.dll.sources
mcs/class/System.Reactive.Core/Makefile
mcs/class/System.Reactive.Linq/Makefile
mcs/class/System.Reactive.Observable.Aliases/Makefile
mcs/class/System.Reactive.PlatformServices/Makefile
mcs/class/System.Reactive.Providers/Makefile
mcs/class/System.Reactive.Runtime.Remoting/Makefile
mcs/class/System.Reactive.Windows.Forms/Makefile
mcs/class/System.Reactive.Windows.Threading/Makefile
mcs/class/System.Runtime.Remoting/Makefile
mcs/class/System.Runtime.Remoting/xammac_net_4_5_System.Runtime.Remoting.dll.sources [new file with mode: 0644]
mcs/class/System.Runtime.Serialization.Formatters.Soap/Makefile
mcs/class/System.Runtime.Serialization.Formatters.Soap/Test/AssemblyInfo.cs
mcs/class/System.Runtime.Serialization/Makefile
mcs/class/System.Runtime.Serialization/ReferenceSources/SR.cs
mcs/class/System.Runtime.Serialization/ReferenceSources/SR.missing.cs [new file with mode: 0644]
mcs/class/System.Runtime.Serialization/ReferenceSources/SR_missing.cs [deleted file]
mcs/class/System.Runtime.Serialization/ReferenceSources/XmlFormatWriterGenerator_static.cs
mcs/class/System.Runtime.Serialization/System.Runtime.Serialization.dll.sources
mcs/class/System.Runtime.Serialization/System.Runtime.Serialization_test.dll.sources
mcs/class/System.Runtime.Serialization/Test/System.Runtime.Serialization/DataContractSerializerTest.cs
mcs/class/System.Runtime.Serialization/Test/System.Runtime.Serialization/Exceptions.cs [new file with mode: 0644]
mcs/class/System.Security/Makefile
mcs/class/System.ServiceModel.Activation/Makefile
mcs/class/System.ServiceModel.Discovery/Makefile
mcs/class/System.ServiceModel.Routing/Makefile
mcs/class/System.ServiceModel/Makefile
mcs/class/System.ServiceModel/System.ServiceModel/EndpointAddress10.cs
mcs/class/System.ServiceModel/System.ServiceModel_test.dll.sources
mcs/class/System.ServiceModel/Test/System.ServiceModel/Bug36080Test.cs [new file with mode: 0644]
mcs/class/System.Threading.Tasks.Dataflow/Makefile
mcs/class/System.Transactions/Makefile
mcs/class/System.Web.DynamicData/Makefile
mcs/class/System.Web.Extensions/Makefile
mcs/class/System.Web.Extensions/System.Web.Script.Serialization/JsonDeserializer.cs
mcs/class/System.Web.Extensions/Test/System.Web.Script.Serialization/JavaScriptSerializerTest.cs
mcs/class/System.Web.Mobile/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Web.Mobile/Makefile [new file with mode: 0644]
mcs/class/System.Web.Mobile/System.Web.Mobile.dll.sources [new file with mode: 0644]
mcs/class/System.Web.RegularExpressions/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Web.RegularExpressions/Makefile [new file with mode: 0644]
mcs/class/System.Web.RegularExpressions/System.Web.RegularExpressions.dll.sources [new file with mode: 0644]
mcs/class/System.Web.Services/Makefile
mcs/class/System.Web/Makefile
mcs/class/System.Web/System.Web.Handlers/AssemblyResourceLoader.cs
mcs/class/System.Web/Test/tools/Makefile
mcs/class/System.Windows.Forms/Makefile
mcs/class/System.Workflow.Activities/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Workflow.Activities/Makefile [new file with mode: 0644]
mcs/class/System.Workflow.Activities/System.Workflow.Activities.dll.sources [new file with mode: 0644]
mcs/class/System.Workflow.ComponentModel/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Workflow.ComponentModel/Makefile [new file with mode: 0644]
mcs/class/System.Workflow.ComponentModel/System.Workflow.ComponentModel.dll.sources [new file with mode: 0644]
mcs/class/System.Workflow.Runtime/Assembly/AssemblyInfo.cs [new file with mode: 0644]
mcs/class/System.Workflow.Runtime/Makefile [new file with mode: 0644]
mcs/class/System.Workflow.Runtime/System.Workflow.Runtime.dll.sources [new file with mode: 0644]
mcs/class/System.XML/Makefile
mcs/class/System/Assembly/AssemblyInfo.cs
mcs/class/System/Assembly/AssemblyInfoEx.cs [new file with mode: 0644]
mcs/class/System/Makefile
mcs/class/System/Microsoft.CSharp/CSharpCodeCompiler.cs
mcs/class/System/Mono.Net.Security/CallbackHelpers.cs
mcs/class/System/Mono.Net.Security/ChainValidationHelper.cs
mcs/class/System/Mono.Net.Security/IMonoSslStream.cs
mcs/class/System/Mono.Net.Security/IMonoTlsProvider.cs
mcs/class/System/Mono.Net.Security/LegacySslStream.cs
mcs/class/System/Mono.Net.Security/MonoDefaultTlsProvider.cs
mcs/class/System/Mono.Net.Security/MonoSslStreamImpl.cs
mcs/class/System/Mono.Net.Security/MonoSslStreamWrapper.cs
mcs/class/System/Mono.Net.Security/MonoTlsProviderFactory.MonoTouch.opt.cs [deleted file]
mcs/class/System/Mono.Net.Security/MonoTlsProviderFactory.cs
mcs/class/System/Mono.Net.Security/MonoTlsProviderFactoryExt.cs [new file with mode: 0644]
mcs/class/System/Mono.Net.Security/MonoTlsProviderImpl.cs
mcs/class/System/Mono.Net.Security/MonoTlsProviderWrapper.cs
mcs/class/System/Mono.Net.Security/MonoTlsStream.cs
mcs/class/System/Mono.Net.Security/SystemCertificateValidator.cs
mcs/class/System/Mono.Security.Interface/MonoTlsProviderFactoryExt.cs [new file with mode: 0644]
mcs/class/System/ReferenceSources/SSPIWrapper.cs
mcs/class/System/System.CodeDom.Compiler/Compiler.cs
mcs/class/System/System.Configuration/AppSettingsReader.cs
mcs/class/System/System.Configuration/ApplicationSettingsBase.cs
mcs/class/System/System.Configuration/ConfigurationSettings.cs
mcs/class/System/System.Configuration/CustomizableFileSettingsProvider.cs
mcs/class/System/System.Configuration/LocalFileSettingsProvider.cs
mcs/class/System/System.Diagnostics/DefaultTraceListener.cs
mcs/class/System/System.Diagnostics/Process.cs
mcs/class/System/System.IO/KeventWatcher.cs
mcs/class/System/System.Net.Mail/SmtpClient.cs
mcs/class/System/System.Net.Security/LocalCertificateSelectionCallback.cs
mcs/class/System/System.Net.Security/RemoteCertificateValidationCallback.cs
mcs/class/System/System.Net.Security/SslStream.cs
mcs/class/System/System.Net.Sockets/SafeSocketHandle.cs
mcs/class/System/System.Net/EndPointListener.cs
mcs/class/System/System.Net/HttpConnection.cs
mcs/class/System/System.Net/HttpListenerRequest.cs
mcs/class/System/System.Security.Authentication.ExtendedProtection.Configuration/ConfigUtil.cs
mcs/class/System/System.Security.Cryptography.X509Certificates/OSX509Certificates.cs
mcs/class/System/System.Security.Cryptography.X509Certificates/X500DistinguishedName.cs
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2.cs
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2Impl.cs [new file with mode: 0644]
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2ImplMono.cs [new file with mode: 0644]
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Chain.cs
mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImpl.cs [new file with mode: 0644]
mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImplMono.cs [new file with mode: 0644]
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Helper2.cs [new file with mode: 0644]
mcs/class/System/System.Security.Cryptography.X509Certificates/X509Store.cs
mcs/class/System/System.dll.sources
mcs/class/System/Test/System.Net.WebSockets/ClientWebSocketTest.cs
mcs/class/System/Test/System.Net/HttpListener2Test.cs
mcs/class/System/Test/System.Net/HttpListenerRequestTest.cs
mcs/class/System/Test/System.Security.Cryptography.X509Certificates/X509Certificate2Test.cs
mcs/class/System/mobile_System.dll.sources
mcs/class/System/monotouch_System.dll.sources
mcs/class/System/monotouch_opt_System.dll.sources [deleted file]
mcs/class/System/monotouch_runtime_opt_System.dll.sources [deleted file]
mcs/class/System/monotouch_tv_opt_System.dll.sources [deleted file]
mcs/class/System/monotouch_tv_runtime_opt_System.dll.sources [deleted file]
mcs/class/System/monotouch_watch_opt_System.dll.sources [deleted file]
mcs/class/System/monotouch_watch_runtime_opt_System.dll.sources [deleted file]
mcs/class/System/xammac_System.dll.sources
mcs/class/System/xammac_net_4_5_System.dll.sources
mcs/class/System/xammac_net_4_5_opt_System.dll.sources [deleted file]
mcs/class/System/xammac_opt_System.dll.sources [deleted file]
mcs/class/WebMatrix.Data/Makefile
mcs/class/WindowsBase/Makefile
mcs/class/WindowsBase/System.Windows.Media/Matrix.cs
mcs/class/WindowsBase/System.Windows/Int32Rect.cs
mcs/class/WindowsBase/System.Windows/Point.cs
mcs/class/WindowsBase/System.Windows/Rect.cs
mcs/class/WindowsBase/System.Windows/Size.cs
mcs/class/WindowsBase/System.Windows/Vector.cs
mcs/class/corlib/Assembly/AssemblyInfo.cs
mcs/class/corlib/CommonCrypto/.gitignore [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/CommonCrypto.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/CorlibExtras.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/CryptorTransform.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/FastCryptorTransform.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/Makefile [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/RC4CommonCrypto.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/RijndaelManaged.cs [new file with mode: 0644]
mcs/class/corlib/CommonCrypto/SecRandom.cs [new file with mode: 0644]
mcs/class/corlib/CoreFoundation/CFHelpers.cs [new file with mode: 0644]
mcs/class/corlib/Makefile
mcs/class/corlib/Mono.Interop/ComInteropProxy.cs
mcs/class/corlib/ReferenceSources/RuntimeType.cs
mcs/class/corlib/ReferenceSources/win32native.cs
mcs/class/corlib/System.Diagnostics/StackFrame.cs
mcs/class/corlib/System.Diagnostics/StackTrace.cs
mcs/class/corlib/System.Globalization/CultureInfo.cs
mcs/class/corlib/System.IO/Directory.cs
mcs/class/corlib/System.IO/DirectoryInfo.cs
mcs/class/corlib/System.IO/File.cs
mcs/class/corlib/System.IO/FileInfo.cs [deleted file]
mcs/class/corlib/System.IO/FileSystemInfo.cs [deleted file]
mcs/class/corlib/System.IO/MonoIOError.cs
mcs/class/corlib/System.IO/MonoIOStat.cs
mcs/class/corlib/System.IO/Path.cs
mcs/class/corlib/System.Reflection.Emit/DerivedTypes.cs
mcs/class/corlib/System.Reflection/MonoField.cs
mcs/class/corlib/System.Reflection/MonoMethod.cs
mcs/class/corlib/System.Runtime.InteropServices/GCHandle.cs
mcs/class/corlib/System.Runtime.InteropServices/Marshal.cs
mcs/class/corlib/System.Security.Cryptography.X509Certificates/INativeCertificateHelper.cs [new file with mode: 0644]
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Certificate.cs
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509CertificateImpl.cs
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs [new file with mode: 0644]
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509CertificateImplMono.cs
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs [new file with mode: 0644]
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.MonoTouch.opt.cs [deleted file]
mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.cs
mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.cs [new file with mode: 0644]
mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.opt.cs [deleted file]
mcs/class/corlib/System.Threading/Monitor.cs
mcs/class/corlib/System.Threading/WaitHandle.cs
mcs/class/corlib/System/Console.cs
mcs/class/corlib/System/Environment.MonoTouch.opt.cs [deleted file]
mcs/class/corlib/System/Environment.cs
mcs/class/corlib/System/Environment.iOS.cs [new file with mode: 0644]
mcs/class/corlib/System/Exception.cs [deleted file]
mcs/class/corlib/System/Guid.MonoTouch.cs [new file with mode: 0644]
mcs/class/corlib/System/Guid.MonoTouch.opt.cs [deleted file]
mcs/class/corlib/System/NotSupportedException.iOS.cs [new file with mode: 0644]
mcs/class/corlib/System/TypeSpec.cs
mcs/class/corlib/System/__ComObject.cs
mcs/class/corlib/Test/System.IO/DirectoryTest.cs
mcs/class/corlib/Test/System.IO/FileInfoTest.cs
mcs/class/corlib/Test/System.Reflection.Emit/DerivedTypesTest.cs
mcs/class/corlib/Test/System.Runtime.ExceptionServices/ExceptionDispatchInfoTest.cs
mcs/class/corlib/Test/System.Security.Cryptography/CspParametersTest.cs
mcs/class/corlib/Test/System.Threading/TimerTest.cs
mcs/class/corlib/Test/System/TypeTest.cs
mcs/class/corlib/corlib.dll.sources
mcs/class/corlib/monotouch_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_corlib.dll.sources
mcs/class/corlib/monotouch_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/monotouch_runtime_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_runtime_corlib.dll.sources
mcs/class/corlib/monotouch_runtime_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/monotouch_tv_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_tv_corlib.dll.sources
mcs/class/corlib/monotouch_tv_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/monotouch_tv_runtime_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_tv_runtime_corlib.dll.sources
mcs/class/corlib/monotouch_tv_runtime_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/monotouch_watch_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_watch_corlib.dll.sources
mcs/class/corlib/monotouch_watch_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/monotouch_watch_runtime_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/monotouch_watch_runtime_corlib.dll.sources
mcs/class/corlib/monotouch_watch_runtime_opt_corlib.dll.sources [deleted file]
mcs/class/corlib/xammac_corlib.dll.exclude.sources [new file with mode: 0644]
mcs/class/corlib/xammac_corlib.dll.sources
mcs/class/corlib/xammac_opt_corlib.dll.sources [deleted file]
mcs/class/dlr/License.html
mcs/class/dlr/License.rtf
mcs/class/monodoc/Makefile
mcs/errors/Makefile
mcs/errors/cs0023-27.cs [new file with mode: 0644]
mcs/errors/cs0023-28.cs [new file with mode: 0644]
mcs/errors/cs0023-29.cs [new file with mode: 0644]
mcs/errors/cs0029-26.cs
mcs/errors/cs0266-30.cs [new file with mode: 0644]
mcs/mcs/Makefile
mcs/mcs/class.cs
mcs/mcs/codegen.cs
mcs/mcs/constant.cs
mcs/mcs/context.cs
mcs/mcs/cs-parser.jay
mcs/mcs/delegate.cs
mcs/mcs/ecore.cs
mcs/mcs/expression.cs
mcs/mcs/iterators.cs
mcs/mcs/settings.cs
mcs/mcs/statement.cs
mcs/mcs/typemanager.cs
mcs/mcs/typespec.cs
mcs/nunit24/ClientUtilities/util/Makefile
mcs/nunit24/ConsoleRunner/nunit-console-exe/Makefile
mcs/nunit24/ConsoleRunner/nunit-console/Makefile
mcs/nunit24/NUnitCore/core/Makefile
mcs/nunit24/NUnitCore/interfaces/Makefile
mcs/nunit24/NUnitExtensions/core/Makefile
mcs/nunit24/NUnitExtensions/framework/Makefile
mcs/nunit24/NUnitFramework/framework/Makefile
mcs/nunit24/NUnitMocks/mocks/Makefile
mcs/tests/dtest-064.cs [new file with mode: 0644]
mcs/tests/gtest-optional-09.cs
mcs/tests/gtest-optional-36.cs [new file with mode: 0644]
mcs/tests/gtest-optional-37.cs [new file with mode: 0644]
mcs/tests/test-933.cs [new file with mode: 0644]
mcs/tests/test-934.cs [new file with mode: 0644]
mcs/tests/test-async-85.cs [new file with mode: 0644]
mcs/tests/test-debug-17-ref.xml
mcs/tests/test-nameof-05.cs
mcs/tests/test-null-operator-04.cs [new file with mode: 0644]
mcs/tests/ver-il-net_4_x.xml
mcs/tools/Makefile
mcs/tools/al/Al.cs
mcs/tools/al/Makefile
mcs/tools/al/al.exe.sources
mcs/tools/browsercaps-updater/Makefile
mcs/tools/cccheck/Makefile
mcs/tools/ccrewrite/Makefile
mcs/tools/cil-stringreplacer/Makefile
mcs/tools/cil-stringreplacer/cil-stringreplacer.cs
mcs/tools/cil-stringreplacer/cil-stringreplacer.csproj [new file with mode: 0644]
mcs/tools/cil-stringreplacer/cil-stringreplacer.exe.sources
mcs/tools/cil-strip/Makefile
mcs/tools/commoncryptogenerator/CommonCryptorGenerator.cs [new file with mode: 0644]
mcs/tools/commoncryptogenerator/CommonDigestGenerator.cs [new file with mode: 0644]
mcs/tools/commoncryptogenerator/Makefile [new file with mode: 0644]
mcs/tools/commoncryptogenerator/commoncryptogenerator.exe.sources [new file with mode: 0644]
mcs/tools/commoncryptogenerator/generator.cs [new file with mode: 0644]
mcs/tools/compiler-tester/Makefile
mcs/tools/compiler-tester/compiler-tester.cs
mcs/tools/corcompare/Makefile
mcs/tools/corcompare/mono-api-html/ApiChange.cs [deleted file]
mcs/tools/corcompare/mono-api-html/ApiDiff.cs [deleted file]
mcs/tools/corcompare/mono-api-html/AssemblyComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/ClassComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/Comparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/ConstructorComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/EventComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/FieldComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/Helpers.cs [deleted file]
mcs/tools/corcompare/mono-api-html/InterfaceComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/MemberComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/MethodComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/NamespaceComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/PropertyComparer.cs [deleted file]
mcs/tools/corcompare/mono-api-html/mono-api-html.csproj [deleted file]
mcs/tools/corcompare/mono-api-info.exe.sources [new file with mode: 0644]
mcs/tools/csharp/Makefile
mcs/tools/culevel/Makefile
mcs/tools/disco/Makefile
mcs/tools/dtd2rng/Makefile
mcs/tools/dtd2xsd/Makefile
mcs/tools/gacutil/Makefile
mcs/tools/gacutil/driver.cs
mcs/tools/genxs/Makefile
mcs/tools/ictool/Makefile
mcs/tools/ikdasm/Makefile
mcs/tools/installutil/Makefile
mcs/tools/installvst/Makefile
mcs/tools/lc/Makefile
mcs/tools/linker-analyzer/Makefile
mcs/tools/linker/Makefile
mcs/tools/linker/Mono.Linker.Steps/MarkStep.cs
mcs/tools/mconfig/Makefile
mcs/tools/mdbdump/Makefile
mcs/tools/mdbrebase/Makefile
mcs/tools/mdoc/Makefile
mcs/tools/mkbundle/Makefile
mcs/tools/mkbundle/mkbundle.cs
mcs/tools/mod/Makefile
mcs/tools/mono-api-html/ApiChange.cs [new file with mode: 0644]
mcs/tools/mono-api-html/ApiDiff.cs [new file with mode: 0644]
mcs/tools/mono-api-html/AssemblyComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/ClassComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/Comparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/ConstructorComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/EventComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/FieldComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/Helpers.cs [new file with mode: 0644]
mcs/tools/mono-api-html/InterfaceComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/Makefile [new file with mode: 0644]
mcs/tools/mono-api-html/MemberComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/MethodComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/NamespaceComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/PropertyComparer.cs [new file with mode: 0644]
mcs/tools/mono-api-html/mono-api-html.csproj [new file with mode: 0644]
mcs/tools/mono-api-html/mono-api-html.exe.sources [new file with mode: 0644]
mcs/tools/mono-configuration-crypto/cli/Makefile
mcs/tools/mono-configuration-crypto/lib/Makefile
mcs/tools/mono-service/Makefile
mcs/tools/mono-shlib-cop/Makefile
mcs/tools/mono-symbolicate/LocationProvider.cs
mcs/tools/mono-symbolicate/Makefile
mcs/tools/mono-symbolicate/SeqPointInfo.cs [new file with mode: 0644]
mcs/tools/mono-symbolicate/Test/symbolicate.expected
mcs/tools/mono-symbolicate/mono-symbolicate.exe.sources
mcs/tools/mono-symbolicate/monosymbolicate.csproj [new file with mode: 0644]
mcs/tools/mono-symbolicate/symbolicate.cs
mcs/tools/mono-xmltool/Makefile
mcs/tools/mono-xsd/Makefile
mcs/tools/monop/Makefile
mcs/tools/msbuild/Makefile
mcs/tools/nunit-lite/NUnitLite/Makefile
mcs/tools/nunit-lite/nunit-lite-console/Makefile
mcs/tools/nunitreport/Makefile
mcs/tools/pdb2mdb/Makefile
mcs/tools/resgen/Makefile
mcs/tools/security/Makefile
mcs/tools/security/certview/Makefile
mcs/tools/sgen/Makefile
mcs/tools/soapsuds/Makefile
mcs/tools/sqlmetal/Makefile
mcs/tools/sqlmetal/Test/.gitattributes [deleted file]
mcs/tools/sqlmetal/Test/AssemblyInfo.cs [deleted file]
mcs/tools/sqlsharp/Makefile
mcs/tools/svcutil/Makefile
mcs/tools/tuner/Makefile
mcs/tools/txt2sr/Makefile
mcs/tools/txt2sr/txt2sr.cs
mcs/tools/wsdl/Makefile
mcs/tools/xbuild/Makefile
mcs/tools/xbuild/SolutionParser.cs
mcs/tools/xbuild/data/12.0/Microsoft.CSharp.targets
mcs/tools/xbuild/data/14.0/Microsoft.CSharp.targets
mcs/tools/xbuild/data/2.0/Microsoft.CSharp.targets
mcs/tools/xbuild/data/3.5/Microsoft.CSharp.targets
mcs/tools/xbuild/data/4.0/Microsoft.CSharp.targets
mcs/tools/xbuild/xbuild.make
mono/arch/amd64/amd64-codegen.h
mono/arch/arm/arm-codegen.h
mono/arch/arm/arm-vfp-codegen.h
mono/arch/arm/arm-wmmx.h
mono/arch/arm64/arm64-codegen.h
mono/arch/mips/mips-codegen.h
mono/arch/ppc/ppc-codegen.h
mono/arch/s390x/s390x-codegen.h
mono/arch/x86/x86-codegen.h
mono/dis/declsec.c
mono/dis/declsec.h
mono/dis/get.c
mono/dis/main.c
mono/io-layer/handles.c
mono/io-layer/io-portability.c
mono/io-layer/io-portability.h
mono/io-layer/io-private.h
mono/io-layer/io-trace.h
mono/io-layer/io.c
mono/io-layer/locking.c
mono/io-layer/posix.c
mono/io-layer/processes.c
mono/io-layer/wthreads.c
mono/metadata/abi-details.h
mono/metadata/appdomain.c
mono/metadata/appdomain.h
mono/metadata/assembly.c
mono/metadata/attach.c
mono/metadata/boehm-gc.c
mono/metadata/class-internals.h
mono/metadata/class.c
mono/metadata/cominterop.c
mono/metadata/console-io.h
mono/metadata/console-null.c
mono/metadata/console-unix.c
mono/metadata/console-win32.c
mono/metadata/coree.c
mono/metadata/coree.h
mono/metadata/debug-helpers.c
mono/metadata/debug-mono-ppdb.c
mono/metadata/debug-mono-ppdb.h
mono/metadata/debug-mono-symfile.c
mono/metadata/debug-mono-symfile.h
mono/metadata/domain-internals.h
mono/metadata/domain.c
mono/metadata/environment.c
mono/metadata/exception.c
mono/metadata/file-io.c
mono/metadata/file-io.h
mono/metadata/file-mmap-posix.c
mono/metadata/file-mmap-windows.c
mono/metadata/file-mmap.h
mono/metadata/filewatcher.c
mono/metadata/gc-internals.h
mono/metadata/gc-stats.c
mono/metadata/gc.c
mono/metadata/handle.c
mono/metadata/handle.h
mono/metadata/icall-def.h
mono/metadata/icall.c
mono/metadata/image-internals.h
mono/metadata/image.c
mono/metadata/jit-info.c
mono/metadata/loader.c
mono/metadata/locales.c
mono/metadata/marshal.c
mono/metadata/mempool.c
mono/metadata/metadata-cross-helpers.c
mono/metadata/metadata-internals.h
mono/metadata/metadata-verify.c
mono/metadata/metadata.c
mono/metadata/metadata.h
mono/metadata/method-builder.c
mono/metadata/monitor.c
mono/metadata/mono-basic-block.c
mono/metadata/mono-basic-block.h
mono/metadata/mono-config-dirs.c
mono/metadata/mono-config.c
mono/metadata/mono-debug.c
mono/metadata/mono-endian.c
mono/metadata/mono-hash.h
mono/metadata/mono-mlist.c
mono/metadata/mono-perfcounters.c
mono/metadata/mono-security.c
mono/metadata/null-gc.c
mono/metadata/number-ms.c
mono/metadata/object-internals.h
mono/metadata/object-offsets.h
mono/metadata/object.c
mono/metadata/object.h
mono/metadata/opcodes.c
mono/metadata/pedump.c
mono/metadata/process.c
mono/metadata/profiler.c
mono/metadata/profiler.h
mono/metadata/rand.c
mono/metadata/rand.h
mono/metadata/reflection-internals.h
mono/metadata/reflection.c
mono/metadata/reflection.h
mono/metadata/remoting.c
mono/metadata/runtime.c
mono/metadata/security-core-clr.c
mono/metadata/security-core-clr.h
mono/metadata/security-manager.c
mono/metadata/security-manager.h
mono/metadata/seq-points-data.h
mono/metadata/sgen-bridge-internals.h
mono/metadata/sgen-bridge.c
mono/metadata/sgen-bridge.h
mono/metadata/sgen-client-mono.h
mono/metadata/sgen-mono.c
mono/metadata/sgen-new-bridge.c
mono/metadata/sgen-old-bridge.c
mono/metadata/sgen-os-coop.c
mono/metadata/sgen-os-mach.c
mono/metadata/sgen-os-posix.c
mono/metadata/sgen-stw.c
mono/metadata/sgen-tarjan-bridge.c
mono/metadata/sgen-toggleref.c
mono/metadata/sgen-toggleref.h
mono/metadata/socket-io.c
mono/metadata/string-icalls.c
mono/metadata/sysmath.c
mono/metadata/sysmath.h
mono/metadata/threadpool-ms-io-epoll.c
mono/metadata/threadpool-ms-io-kqueue.c
mono/metadata/threadpool-ms-io-poll.c
mono/metadata/threadpool-ms-io.c
mono/metadata/threadpool-ms.c
mono/metadata/threadpool-ms.h
mono/metadata/threads-types.h
mono/metadata/threads.c
mono/metadata/threads.h
mono/metadata/verify.c
mono/mini/Makefile.am.in
mono/mini/aot-compiler.c
mono/mini/aot-runtime.c
mono/mini/arch-stubs.c
mono/mini/bench.cs
mono/mini/branch-opts.c
mono/mini/cfgdump.c [new file with mode: 0644]
mono/mini/cfgdump.h [new file with mode: 0644]
mono/mini/cpu-arm.md
mono/mini/cpu-arm64.md
mono/mini/debugger-agent.c
mono/mini/decompose.c
mono/mini/dominators.c
mono/mini/driver.c
mono/mini/dwarfwriter.c
mono/mini/dwarfwriter.h
mono/mini/exceptions-amd64.c
mono/mini/exceptions-arm.c
mono/mini/exceptions-arm64.c
mono/mini/exceptions-ia64.c
mono/mini/exceptions-mips.c
mono/mini/exceptions-ppc.c
mono/mini/exceptions-s390x.c
mono/mini/exceptions-sparc.c
mono/mini/exceptions-x86.c
mono/mini/genmdesc.c
mono/mini/gshared.cs
mono/mini/image-writer.c
mono/mini/jit-icalls.c
mono/mini/liveness.c
mono/mini/llvm-jit.cpp
mono/mini/local-propagation.c
mono/mini/main.c
mono/mini/method-to-ir.c
mono/mini/mini-amd64-gsharedvt.c [new file with mode: 0644]
mono/mini/mini-amd64-gsharedvt.h [new file with mode: 0644]
mono/mini/mini-amd64.c
mono/mini/mini-amd64.h
mono/mini/mini-arm-gsharedvt.c [new file with mode: 0644]
mono/mini/mini-arm-tls.S
mono/mini/mini-arm.c
mono/mini/mini-arm.h
mono/mini/mini-arm64-gsharedvt.c [new file with mode: 0644]
mono/mini/mini-arm64-gsharedvt.h [new file with mode: 0644]
mono/mini/mini-arm64.c
mono/mini/mini-arm64.h
mono/mini/mini-codegen.c
mono/mini/mini-cross-helpers.c
mono/mini/mini-darwin.c
mono/mini/mini-exceptions-native-unwinder.c [new file with mode: 0644]
mono/mini/mini-exceptions.c
mono/mini/mini-gc.c
mono/mini/mini-generic-sharing.c
mono/mini/mini-llvm-cpp.cpp
mono/mini/mini-llvm.c
mono/mini/mini-native-types.c
mono/mini/mini-ops.h
mono/mini/mini-posix.c
mono/mini/mini-runtime.c
mono/mini/mini-trampolines.c
mono/mini/mini-windows.c
mono/mini/mini-x86-gsharedvt.c [new file with mode: 0644]
mono/mini/mini-x86.c
mono/mini/mini-x86.h
mono/mini/mini.c
mono/mini/mini.h
mono/mini/seq-points.c
mono/mini/seq-points.h
mono/mini/ssa.c
mono/mini/test_op_il_seq_point.sh
mono/mini/trace.c
mono/mini/tramp-amd64-gsharedvt.c [new file with mode: 0644]
mono/mini/tramp-amd64.c
mono/mini/tramp-arm-gsharedvt.c [new file with mode: 0644]
mono/mini/tramp-arm.c
mono/mini/tramp-arm64-gsharedvt.c [new file with mode: 0644]
mono/mini/tramp-arm64.c
mono/mini/tramp-s390x.c
mono/mini/tramp-x86-gsharedvt.c [new file with mode: 0644]
mono/mini/tramp-x86.c
mono/mini/unwind.c
mono/mini/xdebug.c
mono/profiler/Makefile.am
mono/profiler/decode.c
mono/profiler/mono-profiler-aot.c
mono/profiler/mono-profiler-iomap.c
mono/profiler/proflog.c
mono/profiler/proflog.h
mono/profiler/ptestrunner.pl
mono/profiler/utils.c
mono/sgen/Makefile.am
mono/sgen/gc-internal-agnostic.h
mono/sgen/sgen-alloc.c
mono/sgen/sgen-archdep.h
mono/sgen/sgen-array-list.c [new file with mode: 0644]
mono/sgen/sgen-array-list.h [new file with mode: 0644]
mono/sgen/sgen-cardtable.c
mono/sgen/sgen-cardtable.h
mono/sgen/sgen-client.h
mono/sgen/sgen-conf.h
mono/sgen/sgen-copy-object.h
mono/sgen/sgen-debug.c
mono/sgen/sgen-descriptor.c
mono/sgen/sgen-descriptor.h
mono/sgen/sgen-fin-weak-hash.c
mono/sgen/sgen-gc.c
mono/sgen/sgen-gc.h
mono/sgen/sgen-gchandles.c
mono/sgen/sgen-gray.c
mono/sgen/sgen-gray.h
mono/sgen/sgen-internal.c
mono/sgen/sgen-layout-stats.c
mono/sgen/sgen-layout-stats.h
mono/sgen/sgen-los.c
mono/sgen/sgen-major-copy-object.h
mono/sgen/sgen-marksweep-drain-gray-stack.h
mono/sgen/sgen-marksweep-scan-object-concurrent.h [deleted file]
mono/sgen/sgen-marksweep.c
mono/sgen/sgen-memory-governor.c
mono/sgen/sgen-memory-governor.h
mono/sgen/sgen-minor-copy-object.h
mono/sgen/sgen-minor-scan-object.h
mono/sgen/sgen-nursery-allocator.c
mono/sgen/sgen-pinning-stats.c
mono/sgen/sgen-pinning.c
mono/sgen/sgen-pinning.h
mono/sgen/sgen-pointer-queue.c
mono/sgen/sgen-pointer-queue.h
mono/sgen/sgen-protocol-def.h
mono/sgen/sgen-protocol.c
mono/sgen/sgen-protocol.h
mono/sgen/sgen-qsort.c
mono/sgen/sgen-qsort.h
mono/sgen/sgen-scan-object.h
mono/sgen/sgen-simple-nursery.c
mono/sgen/sgen-split-nursery.c
mono/sgen/sgen-tagged-pointer.h
mono/sgen/sgen-thread-pool.c
mono/sgen/sgen-thread-pool.h
mono/sgen/sgen-workers.c
mono/sgen/sgen-workers.h
mono/tests/Makefile.am
mono/tests/appdomain-unload.cs
mono/tests/bug-29585.cs [new file with mode: 0644]
mono/tests/libtest.c
mono/tests/pinvoke2.cs
mono/tests/pinvoke3.cs
mono/tests/pinvoke_ppcc.cs
mono/tests/pinvoke_ppcd.cs
mono/tests/pinvoke_ppcf.cs
mono/tests/pinvoke_ppci.cs
mono/tests/pinvoke_ppcs.cs
mono/tests/sgen-bridge-gchandle.cs [new file with mode: 0644]
mono/tests/sgen-toggleref.cs
mono/tests/test-runner.cs
mono/tests/verifier/AssemblyRunner.cs
mono/tests/verifier/BatchCompiler.cs
mono/tests/verifier/COPYING.LIB [deleted file]
mono/tests/verifier/Makefile
mono/tests/verifier/make_access_test.sh
mono/tests/verifier/make_bad_op_test.sh
mono/tests/verifier/make_bin_test.sh
mono/tests/verifier/make_boxed_genarg_test.sh
mono/tests/verifier/make_branch_test.sh
mono/tests/verifier/make_call_test.sh
mono/tests/verifier/make_cmmp_test.sh
mono/tests/verifier/make_cpobj_test.sh
mono/tests/verifier/make_cross_nested_access_test.sh
mono/tests/verifier/make_ctor_test.sh
mono/tests/verifier/make_delegate_compat_test.sh
mono/tests/verifier/make_double_nesting_test.sh
mono/tests/verifier/make_exception_overlap_test.sh
mono/tests/verifier/make_field_store_test.sh
mono/tests/verifier/make_initobj_test.sh
mono/tests/verifier/make_ldobj_test.sh
mono/tests/verifier/make_localloc_test.sh
mono/tests/verifier/make_nested_access_test.sh
mono/tests/verifier/make_obj_store_test.sh
mono/tests/verifier/make_overlapped_test.sh
mono/tests/verifier/make_stobj_test.sh
mono/tests/verifier/make_switch_test.sh
mono/tests/verifier/make_tail_call_test.sh
mono/tests/verifier/make_tests.sh
mono/tests/verifier/make_unbox_test.sh
mono/unit-tests/test-conc-hashtable.c
mono/unit-tests/test-memfuncs.c
mono/unit-tests/test-mono-handle.c
mono/unit-tests/test-sgen-qsort.c
mono/utils/atomic.c
mono/utils/atomic.h
mono/utils/checked-build.c
mono/utils/checked-build.h
mono/utils/dlmalloc.h
mono/utils/gc_wrapper.h
mono/utils/hazard-pointer.c
mono/utils/hazard-pointer.h
mono/utils/json.c
mono/utils/json.h
mono/utils/lock-free-alloc.c
mono/utils/lock-free-alloc.h
mono/utils/lock-free-array-queue.c
mono/utils/lock-free-array-queue.h
mono/utils/lock-free-queue.c
mono/utils/lock-free-queue.h
mono/utils/mach-support.c
mono/utils/memfuncs.c
mono/utils/memfuncs.h
mono/utils/mono-compiler.h
mono/utils/mono-complex.h
mono/utils/mono-conc-hashtable.c
mono/utils/mono-context.c
mono/utils/mono-context.h
mono/utils/mono-counters.c
mono/utils/mono-counters.h
mono/utils/mono-dl-darwin.c
mono/utils/mono-dl-fallback.h
mono/utils/mono-dl-posix.c
mono/utils/mono-dl-windows.c
mono/utils/mono-dl.c
mono/utils/mono-embed.c
mono/utils/mono-error-internals.h
mono/utils/mono-error.c
mono/utils/mono-filemap.c
mono/utils/mono-hwcap-arm.c
mono/utils/mono-hwcap-arm64.c
mono/utils/mono-hwcap-ia64.c
mono/utils/mono-hwcap-mips.c
mono/utils/mono-hwcap-ppc.c
mono/utils/mono-hwcap-s390x.c
mono/utils/mono-hwcap-sparc.c
mono/utils/mono-hwcap-x86.c
mono/utils/mono-hwcap.c
mono/utils/mono-lazy-init.h
mono/utils/mono-linked-list-set.c
mono/utils/mono-linked-list-set.h
mono/utils/mono-machine.h
mono/utils/mono-memory-model.h
mono/utils/mono-mmap-internals.h
mono/utils/mono-mmap.c
mono/utils/mono-os-mutex.h
mono/utils/mono-os-semaphore.h
mono/utils/mono-proclib.c
mono/utils/mono-rand.c
mono/utils/mono-sigcontext.h
mono/utils/mono-signal-handler.h
mono/utils/mono-stack-unwinding.h
mono/utils/mono-threads-android.c
mono/utils/mono-threads-coop.c
mono/utils/mono-threads-mach-abort-syscall.c
mono/utils/mono-threads-mach.c
mono/utils/mono-threads-posix-signals.c
mono/utils/mono-threads-posix-signals.h
mono/utils/mono-threads-posix.c
mono/utils/mono-threads-state-machine.c
mono/utils/mono-threads.c
mono/utils/mono-threads.h
mono/utils/mono-time.c
mono/utils/mono-tls.h
mono/utils/monobitset.h
mono/utils/parse.c
mono/utils/parse.h
msvc/libmono.vcxproj
msvc/libmonoruntime.vcxproj
msvc/mono.def
msvc/monosgen.def
scripts/.gitignore
scripts/Makefile.am
scripts/babysitter [deleted file]
scripts/ci/babysitter [new file with mode: 0755]
scripts/ci/run-jenkins.sh [new file with mode: 0755]
scripts/ci/run-step.sh [new file with mode: 0755]
tools/offsets-tool/.gitignore [new file with mode: 0644]
tools/offsets-tool/Makefile [new file with mode: 0644]
tools/offsets-tool/MonoAotOffsetsDumper.cs [new file with mode: 0644]
winconfig.h

index 230a4505f08c0bbb000f5582184eee1e8111f0f9..ed8d6fe7cc5ac74d975dfc69afdd0d3de2abf69b 100644 (file)
@@ -21,29 +21,18 @@ investigate bugs, regressions and problems.
 License
 =======
 
-The Mono project uses the MIT X11, GNU LGPL version 2 and the Apache
-License 2.0.  We also imported some Microsoft code licensed under the
-open source Microsoft Public License.
+The Mono runtime, compilers, and tools and most of the class libraries
+are licensed under the MIT license. But include some bits of code
+licensed under different licenses. The exact list is [available here] (https://github.com/mono/mono/blob/master/LICENSE).
 
 Different parts of Mono use different licenses.  The actual details of
 which licenses are used for which parts are detailed on the LICENSE
 file in this directory.
 
-When contributing code, make sure that your contribution falls under
-the appropriate license.  For example, contributions to code licensed
-under MIT/X11 code, should be MIT/X11 code.
-
-The runtime (`mono/...`) is a special case.  The code is dual-licensed
-by Xamarin under both the GNU LGPL v2 license and is also available
-under commercial terms.  For the runtime, you should either sign an
-agreement that grants Xamarin the rights to relicense your code under
-other licenses other than the LGPL v2 or your contribution must be
-made as an MIT/X11 license which grants us the same rights, but
-involves no paperwork.  For the latter case, please specify on your
-commit(s) that you are licensing the changes under MIT/X11.
-
-For other parts of the project that are dual-licensed, please state
-on your commit(s) what license you are contributing the changes under.
+CLA
+=======
+
+Contributions are now taken under the [.NET Foundation CLA] (https://cla2.dotnetfoundation.org/). 
 
 Testing
 =======
index 2f3b220f877d4c7c050be2602426412a691fdc0f..5fefc97aa295a4fd4d66c56ca365e9f323479fac 100644 (file)
@@ -1,501 +1 @@
-
-The Mono runtime is licensed under the terms of the GNU 
-Library General Public License, version 2.
-
-The eglib directory is licensed under the terms of the MIT
-X11 license and is a drop-in replacement for Mono's use of
-glib 2.0 (which was LGPL).
-
-The Boehm licensing information is in the libgc directory
-
-The SGen Garbage Collector is under the terms of the MIT X11
-license
-
-The class libraries under mono/mcs are unless otherwise stated
-under the MIT X11 license.
-
-Open source Microsoft code is licensed under the original terms
-which is either MS-PL for older components, or dual licensed
-MS-PL/Apache2 licensed.
-               GNU LIBRARY GENERAL PUBLIC LICENSE
-                      Version 2, June 1991
-
- Copyright (C) 1991 Free Software Foundation, Inc.
-                    675 Mass Ave, Cambridge, MA 02139, USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
-[This is the first released version of the library GPL.  It is
- numbered 2 because it goes with version 2 of the ordinary GPL.]
-
-                           Preamble
-
-  The licenses for most software are designed to take away your
-freedom to share and change it.  By contrast, the GNU General Public
-Licenses are intended to guarantee your freedom to share and change
-free software--to make sure the software is free for all its users.
-
-  This license, the Library General Public License, applies to some
-specially designated Free Software Foundation software, and to any
-other libraries whose authors decide to use it.  You can use it for
-your libraries, too.
-
-  When we speak of free software, we are referring to freedom, not
-price.  Our General Public Licenses are designed to make sure that you
-have the freedom to distribute copies of free software (and charge for
-this service if you wish), that you receive source code or can get it
-if you want it, that you can change the software or use pieces of it
-in new free programs; and that you know you can do these things.
-
-  To protect your rights, we need to make restrictions that forbid
-anyone to deny you these rights or to ask you to surrender the rights.
-These restrictions translate to certain responsibilities for you if
-you distribute copies of the library, or if you modify it.
-
-  For example, if you distribute copies of the library, whether gratis
-or for a fee, you must give the recipients all the rights that we gave
-you.  You must make sure that they, too, receive or can get the source
-code.  If you link a program with the library, you must provide
-complete object files to the recipients so that they can relink them
-with the library, after making changes to the library and recompiling
-it.  And you must show them these terms so they know their rights.
-
-  Our method of protecting your rights has two steps: (1) copyright
-the library, and (2) offer you this license which gives you legal
-permission to copy, distribute and/or modify the library.
-
-  Also, for each distributor's protection, we want to make certain
-that everyone understands that there is no warranty for this free
-library.  If the library is modified by someone else and passed on, we
-want its recipients to know that what they have is not the original
-version, so that any problems introduced by others will not reflect on
-the original authors' reputations.
-\f
-  Finally, any free program is threatened constantly by software
-patents.  We wish to avoid the danger that companies distributing free
-software will individually obtain patent licenses, thus in effect
-transforming the program into proprietary software.  To prevent this,
-we have made it clear that any patent must be licensed for everyone's
-free use or not licensed at all.
-
-  Most GNU software, including some libraries, is covered by the ordinary
-GNU General Public License, which was designed for utility programs.  This
-license, the GNU Library General Public License, applies to certain
-designated libraries.  This license is quite different from the ordinary
-one; be sure to read it in full, and don't assume that anything in it is
-the same as in the ordinary license.
-
-  The reason we have a separate public license for some libraries is that
-they blur the distinction we usually make between modifying or adding to a
-program and simply using it.  Linking a program with a library, without
-changing the library, is in some sense simply using the library, and is
-analogous to running a utility program or application program.  However, in
-a textual and legal sense, the linked executable is a combined work, a
-derivative of the original library, and the ordinary General Public License
-treats it as such.
-
-  Because of this blurred distinction, using the ordinary General
-Public License for libraries did not effectively promote software
-sharing, because most developers did not use the libraries.  We
-concluded that weaker conditions might promote sharing better.
-
-  However, unrestricted linking of non-free programs would deprive the
-users of those programs of all benefit from the free status of the
-libraries themselves.  This Library General Public License is intended to
-permit developers of non-free programs to use free libraries, while
-preserving your freedom as a user of such programs to change the free
-libraries that are incorporated in them.  (We have not seen how to achieve
-this as regards changes in header files, but we have achieved it as regards
-changes in the actual functions of the Library.)  The hope is that this
-will lead to faster development of free libraries.
-
-  The precise terms and conditions for copying, distribution and
-modification follow.  Pay close attention to the difference between a
-"work based on the library" and a "work that uses the library".  The
-former contains code derived from the library, while the latter only
-works together with the library.
-
-  Note that it is possible for a library to be covered by the ordinary
-General Public License rather than by this special one.
-\f
-                 GNU LIBRARY GENERAL PUBLIC LICENSE
-   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
-  0. This License Agreement applies to any software library which
-contains a notice placed by the copyright holder or other authorized
-party saying it may be distributed under the terms of this Library
-General Public License (also called "this License").  Each licensee is
-addressed as "you".
-
-  A "library" means a collection of software functions and/or data
-prepared so as to be conveniently linked with application programs
-(which use some of those functions and data) to form executables.
-
-  The "Library", below, refers to any such software library or work
-which has been distributed under these terms.  A "work based on the
-Library" means either the Library or any derivative work under
-copyright law: that is to say, a work containing the Library or a
-portion of it, either verbatim or with modifications and/or translated
-straightforwardly into another language.  (Hereinafter, translation is
-included without limitation in the term "modification".)
-
-  "Source code" for a work means the preferred form of the work for
-making modifications to it.  For a library, complete source code means
-all the source code for all modules it contains, plus any associated
-interface definition files, plus the scripts used to control compilation
-and installation of the library.
-
-  Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope.  The act of
-running a program using the Library is not restricted, and output from
-such a program is covered only if its contents constitute a work based
-on the Library (independent of the use of the Library in a tool for
-writing it).  Whether that is true depends on what the Library does
-and what the program that uses the Library does.
-  
-  1. You may copy and distribute verbatim copies of the Library's
-complete source code as you receive it, in any medium, provided that
-you conspicuously and appropriately publish on each copy an
-appropriate copyright notice and disclaimer of warranty; keep intact
-all the notices that refer to this License and to the absence of any
-warranty; and distribute a copy of this License along with the
-Library.
-
-  You may charge a fee for the physical act of transferring a copy,
-and you may at your option offer warranty protection in exchange for a
-fee.
-\f
-  2. You may modify your copy or copies of the Library or any portion
-of it, thus forming a work based on the Library, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
-    a) The modified work must itself be a software library.
-
-    b) You must cause the files modified to carry prominent notices
-    stating that you changed the files and the date of any change.
-
-    c) You must cause the whole of the work to be licensed at no
-    charge to all third parties under the terms of this License.
-
-    d) If a facility in the modified Library refers to a function or a
-    table of data to be supplied by an application program that uses
-    the facility, other than as an argument passed when the facility
-    is invoked, then you must make a good faith effort to ensure that,
-    in the event an application does not supply such function or
-    table, the facility still operates, and performs whatever part of
-    its purpose remains meaningful.
-
-    (For example, a function in a library to compute square roots has
-    a purpose that is entirely well-defined independent of the
-    application.  Therefore, Subsection 2d requires that any
-    application-supplied function or table used by this function must
-    be optional: if the application does not supply it, the square
-    root function must still compute square roots.)
-
-These requirements apply to the modified work as a whole.  If
-identifiable sections of that work are not derived from the Library,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works.  But when you
-distribute the same sections as part of a whole which is a work based
-on the Library, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote
-it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Library.
-
-In addition, mere aggregation of another work not based on the Library
-with the Library (or with a work based on the Library) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
-  3. You may opt to apply the terms of the ordinary GNU General Public
-License instead of this License to a given copy of the Library.  To do
-this, you must alter all the notices that refer to this License, so
-that they refer to the ordinary GNU General Public License, version 2,
-instead of to this License.  (If a newer version than version 2 of the
-ordinary GNU General Public License has appeared, then you can specify
-that version instead if you wish.)  Do not make any other change in
-these notices.
-\f
-  Once this change is made in a given copy, it is irreversible for
-that copy, so the ordinary GNU General Public License applies to all
-subsequent copies and derivative works made from that copy.
-
-  This option is useful when you wish to copy part of the code of
-the Library into a program that is not a library.
-
-  4. You may copy and distribute the Library (or a portion or
-derivative of it, under Section 2) in object code or executable form
-under the terms of Sections 1 and 2 above provided that you accompany
-it with the complete corresponding machine-readable source code, which
-must be distributed under the terms of Sections 1 and 2 above on a
-medium customarily used for software interchange.
-
-  If distribution of object code is made by offering access to copy
-from a designated place, then offering equivalent access to copy the
-source code from the same place satisfies the requirement to
-distribute the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
-  5. A program that contains no derivative of any portion of the
-Library, but is designed to work with the Library by being compiled or
-linked with it, is called a "work that uses the Library".  Such a
-work, in isolation, is not a derivative work of the Library, and
-therefore falls outside the scope of this License.
-
-  However, linking a "work that uses the Library" with the Library
-creates an executable that is a derivative of the Library (because it
-contains portions of the Library), rather than a "work that uses the
-library".  The executable is therefore covered by this License.
-Section 6 states terms for distribution of such executables.
-
-  When a "work that uses the Library" uses material from a header file
-that is part of the Library, the object code for the work may be a
-derivative work of the Library even though the source code is not.
-Whether this is true is especially significant if the work can be
-linked without the Library, or if the work is itself a library.  The
-threshold for this to be true is not precisely defined by law.
-
-  If such an object file uses only numerical parameters, data
-structure layouts and accessors, and small macros and small inline
-functions (ten lines or less in length), then the use of the object
-file is unrestricted, regardless of whether it is legally a derivative
-work.  (Executables containing this object code plus portions of the
-Library will still fall under Section 6.)
-
-  Otherwise, if the work is a derivative of the Library, you may
-distribute the object code for the work under the terms of Section 6.
-Any executables containing that work also fall under Section 6,
-whether or not they are linked directly with the Library itself.
-\f
-  6. As an exception to the Sections above, you may also compile or
-link a "work that uses the Library" with the Library to produce a
-work containing portions of the Library, and distribute that work
-under terms of your choice, provided that the terms permit
-modification of the work for the customer's own use and reverse
-engineering for debugging such modifications.
-
-  You must give prominent notice with each copy of the work that the
-Library is used in it and that the Library and its use are covered by
-this License.  You must supply a copy of this License.  If the work
-during execution displays copyright notices, you must include the
-copyright notice for the Library among them, as well as a reference
-directing the user to the copy of this License.  Also, you must do one
-of these things:
-
-    a) Accompany the work with the complete corresponding
-    machine-readable source code for the Library including whatever
-    changes were used in the work (which must be distributed under
-    Sections 1 and 2 above); and, if the work is an executable linked
-    with the Library, with the complete machine-readable "work that
-    uses the Library", as object code and/or source code, so that the
-    user can modify the Library and then relink to produce a modified
-    executable containing the modified Library.  (It is understood
-    that the user who changes the contents of definitions files in the
-    Library will not necessarily be able to recompile the application
-    to use the modified definitions.)
-
-    b) Accompany the work with a written offer, valid for at
-    least three years, to give the same user the materials
-    specified in Subsection 6a, above, for a charge no more
-    than the cost of performing this distribution.
-
-    c) If distribution of the work is made by offering access to copy
-    from a designated place, offer equivalent access to copy the above
-    specified materials from the same place.
-
-    d) Verify that the user has already received a copy of these
-    materials or that you have already sent this user a copy.
-
-  For an executable, the required form of the "work that uses the
-Library" must include any data and utility programs needed for
-reproducing the executable from it.  However, as a special exception,
-the source code distributed need not include anything that is normally
-distributed (in either source or binary form) with the major
-components (compiler, kernel, and so on) of the operating system on
-which the executable runs, unless that component itself accompanies
-the executable.
-
-  It may happen that this requirement contradicts the license
-restrictions of other proprietary libraries that do not normally
-accompany the operating system.  Such a contradiction means you cannot
-use both them and the Library together in an executable that you
-distribute.
-\f
-  7. You may place library facilities that are a work based on the
-Library side-by-side in a single library together with other library
-facilities not covered by this License, and distribute such a combined
-library, provided that the separate distribution of the work based on
-the Library and of the other library facilities is otherwise
-permitted, and provided that you do these two things:
-
-    a) Accompany the combined library with a copy of the same work
-    based on the Library, uncombined with any other library
-    facilities.  This must be distributed under the terms of the
-    Sections above.
-
-    b) Give prominent notice with the combined library of the fact
-    that part of it is a work based on the Library, and explaining
-    where to find the accompanying uncombined form of the same work.
-
-  8. You may not copy, modify, sublicense, link with, or distribute
-the Library except as expressly provided under this License.  Any
-attempt otherwise to copy, modify, sublicense, link with, or
-distribute the Library is void, and will automatically terminate your
-rights under this License.  However, parties who have received copies,
-or rights, from you under this License will not have their licenses
-terminated so long as such parties remain in full compliance.
-
-  9. You are not required to accept this License, since you have not
-signed it.  However, nothing else grants you permission to modify or
-distribute the Library or its derivative works.  These actions are
-prohibited by law if you do not accept this License.  Therefore, by
-modifying or distributing the Library (or any work based on the
-Library), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Library or works based on it.
-
-  10. Each time you redistribute the Library (or any work based on the
-Library), the recipient automatically receives a license from the
-original licensor to copy, distribute, link with or modify the Library
-subject to these terms and conditions.  You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties to
-this License.
-\f
-  11. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License.  If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Library at all.  For example, if a patent
-license would not permit royalty-free redistribution of the Library by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Library.
-
-If any portion of this section is held invalid or unenforceable under any
-particular circumstance, the balance of the section is intended to apply,
-and the section as a whole is intended to apply in other circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system which is
-implemented by public license practices.  Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
-  12. If the distribution and/or use of the Library is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Library under this License may add
-an explicit geographical distribution limitation excluding those countries,
-so that distribution is permitted only in or among countries not thus
-excluded.  In such case, this License incorporates the limitation as if
-written in the body of this License.
-
-  13. The Free Software Foundation may publish revised and/or new
-versions of the Library General Public License from time to time.
-Such new versions will be similar in spirit to the present version,
-but may differ in detail to address new problems or concerns.
-
-Each version is given a distinguishing version number.  If the Library
-specifies a version number of this License which applies to it and
-"any later version", you have the option of following the terms and
-conditions either of that version or of any later version published by
-the Free Software Foundation.  If the Library does not specify a
-license version number, you may choose any version ever published by
-the Free Software Foundation.
-\f
-  14. If you wish to incorporate parts of the Library into other free
-programs whose distribution conditions are incompatible with these,
-write to the author to ask for permission.  For software which is
-copyrighted by the Free Software Foundation, write to the Free
-Software Foundation; we sometimes make exceptions for this.  Our
-decision will be guided by the two goals of preserving the free status
-of all derivatives of our free software and of promoting the sharing
-and reuse of software generally.
-
-                           NO WARRANTY
-
-  15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
-WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
-EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
-OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
-KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
-IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
-PURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
-LIBRARY IS WITH YOU.  SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
-THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
-
-  16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
-WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
-AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
-FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
-CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
-LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
-RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
-FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
-SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
-DAMAGES.
-
-                    END OF TERMS AND CONDITIONS
-\f
-     Appendix: How to Apply These Terms to Your New Libraries
-
-  If you develop a new library, and you want it to be of the greatest
-possible use to the public, we recommend making it free software that
-everyone can redistribute and change.  You can do so by permitting
-redistribution under these terms (or, alternatively, under the terms of the
-ordinary General Public License).
-
-  To apply these terms, attach the following notices to the library.  It is
-safest to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least the
-"copyright" line and a pointer to where the full notice is found.
-
-    <one line to give the library's name and a brief idea of what it does.>
-    Copyright (C) <year>  <name of author>
-
-    This library is free software; you can redistribute it and/or
-    modify it under the terms of the GNU Library General Public
-    License as published by the Free Software Foundation; either
-    version 2 of the License, or (at your option) any later version.
-
-    This library 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
-    Library General Public License for more details.
-
-    You should have received a copy of the GNU Library General Public
-    License along with this library; if not, write to the Free
-    Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-
-Also add information on how to contact you by electronic and paper mail.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the library, if
-necessary.  Here is a sample; alter the names:
-
-  Yoyodyne, Inc., hereby disclaims all copyright interest in the
-  library `Frob' (a library for tweaking knobs) written by James Random Hacker.
-
-  <signature of Ty Coon>, 1 April 1990
-  Ty Coon, President of Vice
-
-That's all there is to it!
+See LICENSE file in the project root for full license information.
\ No newline at end of file
diff --git a/LICENSE b/LICENSE
index ad5cbb429ff8967d651bee84d1d13edfb8439474..71bfc9eb4ce92efb3aaefacf0a417e558faf3901 100644 (file)
--- a/LICENSE
+++ b/LICENSE
 
-Mono is made up of many pieces of code, all of them open source, but
-different pieces of Mono use different licensing terms.
+In general, the runtime and its class libraries are licensed under the
+terms of the MIT license, and some third party code is licensed under
+the 3-clause BSD license.  See the file "PATENTS.TXT" for Microsoft's
+patent grant on the Mono codebase.
 
-For comments, corrections and updates, please contact mono@xamarin.com
+The Mono distribution does include a handful of pieces of code that
+are used during the build system and are covered under different
+licenses, those include:
 
-* Dual Licensing
+Build Time Code
+===============
 
-       Parts of Mono are dual licensed, they are available to the
-       public in GPL or LGPL forms, but we also offer those pieces
-       under commercial terms from Xamarin for the cases where the
-       GPL and the LGPL are not suitable.
+This is code that is used at build time, or during the maintenance of
+Mono itself, and does not end up in the redistributable part of Mono:
 
-       We have tried to pick the licenses that will maximize adoption
-       of Mono, so we tend to use the MIT X11 or LGPL liceses.
+* gettext
 
-       Contributions to dual-licensed module require that the author
-       contributes the code under the terms of the MIT X11 code, or
-       to sign an agreement that allows Novell to redistribute the
-       code under other licenses.
+  m4 source files used to probe features at build time: GPL
 
-       Contributions for other modules should be under the same license
-       terms as the rest of the module, or under MIT X11 terms. 
+* Benchmark Source Files
 
-       For the actual license links in the Mono distribution see the
-       bottom of this file.
+  Logic.cs and zipmark.cs are GPL source files.
 
-       If you need further information, please contact mono@xamarin.com
+* mono/docs/HtmlAgilityPack
 
-* The Modules
+  MS-PL licensed
 
-** mono/mono: the Mono VM
+* mcs/jay: 4-clause BSD licensed
 
-       This code is dual licensed under the LGPL or commercial licenses. 
+* mcs/nunit24: MS-PL
 
-       The LGPL ensures that Mono can be used in most scenarios, but
-       gives Xamarin the flexibility to relicense the code for
-       embedded systems, static linking or commercial settings where
-       the LGPL can not be used.
+* mcs/class/I18N/mklist.sh, tools/cvt.sh: GNU GPLv2
 
-       We consider non-LGPL use instances where you use this on an
-       embedded system where the end user is not able to upgrade the
-       Mono VM or Moonlight installation or distribution that is part
-       of your product (Section 6 and 7), you would have to obtain a
-       commercial license from Xamarin (consider software burned into
-       a ROM, systems where end users would not be able to upgrade,
-       an embedded console, a game console that imposes limitations
-       on the distribution and access to the code, a phone platform
-       that prevents end users from upgrading Moonlight).
-       
-       Contact mono@xamarin.com for details on obtaining the Mono
-       runtime under other terms.
+Runtime Code
+============
 
-** mono/support: MonoPosixHelper and support code
+The following code is linked with the final Mono runtime, the libmono
+embeddable runtime:
 
-       This code is dual licensed under the LGPL or commercial licenses, with
-       the same guidelines as mono/mono code.
+* support/minizip: BSD license.
 
-       The ZLib files are included under a "new BSD"-style license.
+* mono/utils/memcheck.h: BSD license, used on debug builds that use Valgrind.
 
-** mono/eglib: Mono's X11 glib implementation
+* mono/utils/freebsd-dwarf.h, freebsd-elf_common.h, freebsd-elf64.h freebsd-elf32.h: BSD license.
 
-       This is a minimal subset of glib that is to be licensed under
-       the terms of the MIT X11, this means that this code can be
-       used for any purposes by anyone.
+* mono/utils/bsearch.c: BSD license.
 
-** mono/arch/*/XXX-codegen.h
+* mono/io-layer/wapi_glob.h, wapi_glob.c: BSD license
 
-       This are C macros that are useful when generating native
-       code on various platforms.   This code is MIT X11 licensed.
+Class Library code
+==================
 
-** mcs/mcs, mcs/gmcs
+These are class libraries that can be loaded by your process:
 
-       The C# Compilers (1.0 and 2.0)
+* mcs/class/RabbitMQ.Client: dual licensed in Apache v2, and Mozilla Public License 1.1
 
-       These compilers are dual licensed under the GPL and MIT X11
-       license terms.
+* mcs/class/Compat.ICSharpCode.SharpZipLib and
+  mcs/class/ICSharpCode.SharpZipLib are GPL with class-path exception.
+  Originates with the SharpDevelop project.
 
-** tests
+* mcs/class/System.Core/System/TimeZoneInfo.Android.cs
 
-       Unless explicitly stated, the tests are under the MIT X11 license.
+  This is a port of Apache 2.0-licensed Android code, and thus is
+  licensed under the Apache 2.0 license
 
-** mcs/class
+           http://www.apache.org/licenses/LICENSE-2.0
 
-       The class libraries developed by the Mono team are licensed
-       under the MIT X11 terms.
+API Documentation
+=================
 
-       In addition to the class libraries developed by the Mono team,
-       there are a number of class libraries that we bundle as part
-       of the distribution that were integrated from third-parties or
-       that contain code that was originally licensed under different
-       terms, these are:
+The API documentation is licensed under the terms of the Creative
+Commons Attribution 4.0 International Public License
 
-           ByteFX.Data: LGPL
 
-           Npgsql: LGPL
+The Licenses
+============
 
-           FirebirdSql.Data.Firebird: Firebird public license.
-               See: mcs/class/FirebirdSql.Data.Firebird/license.txt
+       These are the licenses used in Mono, the files are located:
 
-            ICSharpCode.SharpZipLib, GPL with exceptions.
-               See: mcs/class/ICSharpCode.SharpZipLib/README
+### MIT X11 License
 
-** mcs/class/System.Core/System/TimeZoneInfo.Android.cs
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
 
-       This is a port of Apache 2.0-licensed Android code, and thus is
-       licensed under the Apache 2.0 license:
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
 
-           http://www.apache.org/licenses/LICENSE-2.0
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
-            
-** mcs/tools
 
-       These are licensed under the MIT X11 license, except where the
-       GPL is explicitly used. 
+### Mozilla.MPL
 
-** mcs/jay
+                          MOZILLA PUBLIC LICENSE
+                                Version 1.1
 
-       This is a port of Berkeley yacc, so it is available under the BSD
-       license.   See the license in the individual C files for details.
+                              ---------------
 
-** mono/man
+1. Definitions.
 
-       Manual pages and Mono documentation are covered by the MIT X11 license. 
+     1.0.1. "Commercial Use" means distribution or otherwise making the
+     Covered Code available to a third party.
 
-* samples
+     1.1. "Contributor" means each entity that creates or contributes to
+     the creation of Modifications.
 
-       The code in the "samples" directory is released under the MIT X11 license.
+     1.2. "Contributor Version" means the combination of the Original
+     Code, prior Modifications used by a Contributor, and the Modifications
+     made by that particular Contributor.
 
-* The Licenses
+     1.3. "Covered Code" means the Original Code or Modifications or the
+     combination of the Original Code and Modifications, in each case
+     including portions thereof.
 
-       These are the licenses used in Mono, the files are located:
+     1.4. "Electronic Distribution Mechanism" means a mechanism generally
+     accepted in the software development community for the electronic
+     transfer of data.
+
+     1.5. "Executable" means Covered Code in any form other than Source
+     Code.
+
+     1.6. "Initial Developer" means the individual or entity identified
+     as the Initial Developer in the Source Code notice required by Exhibit
+     A.
+
+     1.7. "Larger Work" means a work which combines Covered Code or
+     portions thereof with code not governed by the terms of this License.
+
+     1.8. "License" means this document.
+
+     1.8.1. "Licensable" means having the right to grant, to the maximum
+     extent possible, whether at the time of the initial grant or
+     subsequently acquired, any and all of the rights conveyed herein.
+
+     1.9. "Modifications" means any addition to or deletion from the
+     substance or structure of either the Original Code or any previous
+     Modifications. When Covered Code is released as a series of files, a
+     Modification is:
+          A. Any addition to or deletion from the contents of a file
+          containing Original Code or previous Modifications.
+
+          B. Any new file that contains any part of the Original Code or
+          previous Modifications.
+
+     1.10. "Original Code" means Source Code of computer software code
+     which is described in the Source Code notice required by Exhibit A as
+     Original Code, and which, at the time of its release under this
+     License is not already Covered Code governed by this License.
+
+     1.10.1. "Patent Claims" means any patent claim(s), now owned or
+     hereafter acquired, including without limitation,  method, process,
+     and apparatus claims, in any patent Licensable by grantor.
+
+     1.11. "Source Code" means the preferred form of the Covered Code for
+     making modifications to it, including all modules it contains, plus
+     any associated interface definition files, scripts used to control
+     compilation and installation of an Executable, or source code
+     differential comparisons against either the Original Code or another
+     well known, available Covered Code of the Contributor's choice. The
+     Source Code can be in a compressed or archival form, provided the
+     appropriate decompression or de-archiving software is widely available
+     for no charge.
+
+     1.12. "You" (or "Your")  means an individual or a legal entity
+     exercising rights under, and complying with all of the terms of, this
+     License or a future version of this License issued under Section 6.1.
+     For legal entities, "You" includes any entity which controls, is
+     controlled by, or is under common control with You. For purposes of
+     this definition, "control" means (a) the power, direct or indirect,
+     to cause the direction or management of such entity, whether by
+     contract or otherwise, or (b) ownership of more than fifty percent
+     (50%) of the outstanding shares or beneficial ownership of such
+     entity.
+
+2. Source Code License.
+
+     2.1. The Initial Developer Grant.
+     The Initial Developer hereby grants You a world-wide, royalty-free,
+     non-exclusive license, subject to third party intellectual property
+     claims:
+          (a)  under intellectual property rights (other than patent or
+          trademark) Licensable by Initial Developer to use, reproduce,
+          modify, display, perform, sublicense and distribute the Original
+          Code (or portions thereof) with or without Modifications, and/or
+          as part of a Larger Work; and
+
+          (b) under Patents Claims infringed by the making, using or
+          selling of Original Code, to make, have made, use, practice,
+          sell, and offer for sale, and/or otherwise dispose of the
+          Original Code (or portions thereof).
+
+          (c) the licenses granted in this Section 2.1(a) and (b) are
+          effective on the date Initial Developer first distributes
+          Original Code under the terms of this License.
+
+          (d) Notwithstanding Section 2.1(b) above, no patent license is
+          granted: 1) for code that You delete from the Original Code; 2)
+          separate from the Original Code;  or 3) for infringements caused
+          by: i) the modification of the Original Code or ii) the
+          combination of the Original Code with other software or devices.
+
+     2.2. Contributor Grant.
+     Subject to third party intellectual property claims, each Contributor
+     hereby grants You a world-wide, royalty-free, non-exclusive license
+
+          (a)  under intellectual property rights (other than patent or
+          trademark) Licensable by Contributor, to use, reproduce, modify,
+          display, perform, sublicense and distribute the Modifications
+          created by such Contributor (or portions thereof) either on an
+          unmodified basis, with other Modifications, as Covered Code
+          and/or as part of a Larger Work; and
+
+          (b) under Patent Claims infringed by the making, using, or
+          selling of  Modifications made by that Contributor either alone
+          and/or in combination with its Contributor Version (or portions
+          of such combination), to make, use, sell, offer for sale, have
+          made, and/or otherwise dispose of: 1) Modifications made by that
+          Contributor (or portions thereof); and 2) the combination of
+          Modifications made by that Contributor with its Contributor
+          Version (or portions of such combination).
+
+          (c) the licenses granted in Sections 2.2(a) and 2.2(b) are
+          effective on the date Contributor first makes Commercial Use of
+          the Covered Code.
+
+          (d)    Notwithstanding Section 2.2(b) above, no patent license is
+          granted: 1) for any code that Contributor has deleted from the
+          Contributor Version; 2)  separate from the Contributor Version;
+          3)  for infringements caused by: i) third party modifications of
+          Contributor Version or ii)  the combination of Modifications made
+          by that Contributor with other software  (except as part of the
+          Contributor Version) or other devices; or 4) under Patent Claims
+          infringed by Covered Code in the absence of Modifications made by
+          that Contributor.
+
+3. Distribution Obligations.
+
+     3.1. Application of License.
+     The Modifications which You create or to which You contribute are
+     governed by the terms of this License, including without limitation
+     Section 2.2. The Source Code version of Covered Code may be
+     distributed only under the terms of this License or a future version
+     of this License released under Section 6.1, and You must include a
+     copy of this License with every copy of the Source Code You
+     distribute. You may not offer or impose any terms on any Source Code
+     version that alters or restricts the applicable version of this
+     License or the recipients' rights hereunder. However, You may include
+     an additional document offering the additional rights described in
+     Section 3.5.
+
+     3.2. Availability of Source Code.
+     Any Modification which You create or to which You contribute must be
+     made available in Source Code form under the terms of this License
+     either on the same media as an Executable version or via an accepted
+     Electronic Distribution Mechanism to anyone to whom you made an
+     Executable version available; and if made available via Electronic
+     Distribution Mechanism, must remain available for at least twelve (12)
+     months after the date it initially became available, or at least six
+     (6) months after a subsequent version of that particular Modification
+     has been made available to such recipients. You are responsible for
+     ensuring that the Source Code version remains available even if the
+     Electronic Distribution Mechanism is maintained by a third party.
+
+     3.3. Description of Modifications.
+     You must cause all Covered Code to which You contribute to contain a
+     file documenting the changes You made to create that Covered Code and
+     the date of any change. You must include a prominent statement that
+     the Modification is derived, directly or indirectly, from Original
+     Code provided by the Initial Developer and including the name of the
+     Initial Developer in (a) the Source Code, and (b) in any notice in an
+     Executable version or related documentation in which You describe the
+     origin or ownership of the Covered Code.
+
+     3.4. Intellectual Property Matters
+          (a) Third Party Claims.
+          If Contributor has knowledge that a license under a third party's
+          intellectual property rights is required to exercise the rights
+          granted by such Contributor under Sections 2.1 or 2.2,
+          Contributor must include a text file with the Source Code
+          distribution titled "LEGAL" which describes the claim and the
+          party making the claim in sufficient detail that a recipient will
+          know whom to contact. If Contributor obtains such knowledge after
+          the Modification is made available as described in Section 3.2,
+          Contributor shall promptly modify the LEGAL file in all copies
+          Contributor makes available thereafter and shall take other steps
+          (such as notifying appropriate mailing lists or newsgroups)
+          reasonably calculated to inform those who received the Covered
+          Code that new knowledge has been obtained.
+
+          (b) Contributor APIs.
+          If Contributor's Modifications include an application programming
+          interface and Contributor has knowledge of patent licenses which
+          are reasonably necessary to implement that API, Contributor must
+          also include this information in the LEGAL file.
+
+               (c)    Representations.
+          Contributor represents that, except as disclosed pursuant to
+          Section 3.4(a) above, Contributor believes that Contributor's
+          Modifications are Contributor's original creation(s) and/or
+          Contributor has sufficient rights to grant the rights conveyed by
+          this License.
+
+     3.5. Required Notices.
+     You must duplicate the notice in Exhibit A in each file of the Source
+     Code.  If it is not possible to put such notice in a particular Source
+     Code file due to its structure, then You must include such notice in a
+     location (such as a relevant directory) where a user would be likely
+     to look for such a notice.  If You created one or more Modification(s)
+     You may add your name as a Contributor to the notice described in
+     Exhibit A.  You must also duplicate this License in any documentation
+     for the Source Code where You describe recipients' rights or ownership
+     rights relating to Covered Code.  You may choose to offer, and to
+     charge a fee for, warranty, support, indemnity or liability
+     obligations to one or more recipients of Covered Code. However, You
+     may do so only on Your own behalf, and not on behalf of the Initial
+     Developer or any Contributor. You must make it absolutely clear than
+     any such warranty, support, indemnity or liability obligation is
+     offered by You alone, and You hereby agree to indemnify the Initial
+     Developer and every Contributor for any liability incurred by the
+     Initial Developer or such Contributor as a result of warranty,
+     support, indemnity or liability terms You offer.
+
+     3.6. Distribution of Executable Versions.
+     You may distribute Covered Code in Executable form only if the
+     requirements of Section 3.1-3.5 have been met for that Covered Code,
+     and if You include a notice stating that the Source Code version of
+     the Covered Code is available under the terms of this License,
+     including a description of how and where You have fulfilled the
+     obligations of Section 3.2. The notice must be conspicuously included
+     in any notice in an Executable version, related documentation or
+     collateral in which You describe recipients' rights relating to the
+     Covered Code. You may distribute the Executable version of Covered
+     Code or ownership rights under a license of Your choice, which may
+     contain terms different from this License, provided that You are in
+     compliance with the terms of this License and that the license for the
+     Executable version does not attempt to limit or alter the recipient's
+     rights in the Source Code version from the rights set forth in this
+     License. If You distribute the Executable version under a different
+     license You must make it absolutely clear that any terms which differ
+     from this License are offered by You alone, not by the Initial
+     Developer or any Contributor. You hereby agree to indemnify the
+     Initial Developer and every Contributor for any liability incurred by
+     the Initial Developer or such Contributor as a result of any such
+     terms You offer.
+
+     3.7. Larger Works.
+     You may create a Larger Work by combining Covered Code with other code
+     not governed by the terms of this License and distribute the Larger
+     Work as a single product. In such a case, You must make sure the
+     requirements of this License are fulfilled for the Covered Code.
+
+4. Inability to Comply Due to Statute or Regulation.
+
+     If it is impossible for You to comply with any of the terms of this
+     License with respect to some or all of the Covered Code due to
+     statute, judicial order, or regulation then You must: (a) comply with
+     the terms of this License to the maximum extent possible; and (b)
+     describe the limitations and the code they affect. Such description
+     must be included in the LEGAL file described in Section 3.4 and must
+     be included with all distributions of the Source Code. Except to the
+     extent prohibited by statute or regulation, such description must be
+     sufficiently detailed for a recipient of ordinary skill to be able to
+     understand it.
+
+5. Application of this License.
+
+     This License applies to code to which the Initial Developer has
+     attached the notice in Exhibit A and to related Covered Code.
+
+6. Versions of the License.
+
+     6.1. New Versions.
+     Netscape Communications Corporation ("Netscape") may publish revised
+     and/or new versions of the License from time to time. Each version
+     will be given a distinguishing version number.
+
+     6.2. Effect of New Versions.
+     Once Covered Code has been published under a particular version of the
+     License, You may always continue to use it under the terms of that
+     version. You may also choose to use such Covered Code under the terms
+     of any subsequent version of the License published by Netscape. No one
+     other than Netscape has the right to modify the terms applicable to
+     Covered Code created under this License.
+
+     6.3. Derivative Works.
+     If You create or use a modified version of this License (which you may
+     only do in order to apply it to code which is not already Covered Code
+     governed by this License), You must (a) rename Your license so that
+     the phrases "Mozilla", "MOZILLAPL", "MOZPL", "Netscape",
+     "MPL", "NPL" or any confusingly similar phrase do not appear in your
+     license (except to note that your license differs from this License)
+     and (b) otherwise make it clear that Your version of the license
+     contains terms which differ from the Mozilla Public License and
+     Netscape Public License. (Filling in the name of the Initial
+     Developer, Original Code or Contributor in the notice described in
+     Exhibit A shall not of themselves be deemed to be modifications of
+     this License.)
+
+7. DISCLAIMER OF WARRANTY.
+
+     COVERED CODE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS,
+     WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
+     WITHOUT LIMITATION, WARRANTIES THAT THE COVERED CODE IS FREE OF
+     DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR NON-INFRINGING.
+     THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE COVERED CODE
+     IS WITH YOU. SHOULD ANY COVERED CODE PROVE DEFECTIVE IN ANY RESPECT,
+     YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER CONTRIBUTOR) ASSUME THE
+     COST OF ANY NECESSARY SERVICING, REPAIR OR CORRECTION. THIS DISCLAIMER
+     OF WARRANTY CONSTITUTES AN ESSENTIAL PART OF THIS LICENSE. NO USE OF
+     ANY COVERED CODE IS AUTHORIZED HEREUNDER EXCEPT UNDER THIS DISCLAIMER.
+
+8. TERMINATION.
+
+     8.1.  This License and the rights granted hereunder will terminate
+     automatically if You fail to comply with terms herein and fail to cure
+     such breach within 30 days of becoming aware of the breach. All
+     sublicenses to the Covered Code which are properly granted shall
+     survive any termination of this License. Provisions which, by their
+     nature, must remain in effect beyond the termination of this License
+     shall survive.
+
+     8.2.  If You initiate litigation by asserting a patent infringement
+     claim (excluding declatory judgment actions) against Initial Developer
+     or a Contributor (the Initial Developer or Contributor against whom
+     You file such action is referred to as "Participant")  alleging that:
+
+     (a)  such Participant's Contributor Version directly or indirectly
+     infringes any patent, then any and all rights granted by such
+     Participant to You under Sections 2.1 and/or 2.2 of this License
+     shall, upon 60 days notice from Participant terminate prospectively,
+     unless if within 60 days after receipt of notice You either: (i)
+     agree in writing to pay Participant a mutually agreeable reasonable
+     royalty for Your past and future use of Modifications made by such
+     Participant, or (ii) withdraw Your litigation claim with respect to
+     the Contributor Version against such Participant.  If within 60 days
+     of notice, a reasonable royalty and payment arrangement are not
+     mutually agreed upon in writing by the parties or the litigation claim
+     is not withdrawn, the rights granted by Participant to You under
+     Sections 2.1 and/or 2.2 automatically terminate at the expiration of
+     the 60 day notice period specified above.
+
+     (b)  any software, hardware, or device, other than such Participant's
+     Contributor Version, directly or indirectly infringes any patent, then
+     any rights granted to You by such Participant under Sections 2.1(b)
+     and 2.2(b) are revoked effective as of the date You first made, used,
+     sold, distributed, or had made, Modifications made by that
+     Participant.
+
+     8.3.  If You assert a patent infringement claim against Participant
+     alleging that such Participant's Contributor Version directly or
+     indirectly infringes any patent where such claim is resolved (such as
+     by license or settlement) prior to the initiation of patent
+     infringement litigation, then the reasonable value of the licenses
+     granted by such Participant under Sections 2.1 or 2.2 shall be taken
+     into account in determining the amount or value of any payment or
+     license.
+
+     8.4.  In the event of termination under Sections 8.1 or 8.2 above,
+     all end user license agreements (excluding distributors and resellers)
+     which have been validly granted by You or any distributor hereunder
+     prior to termination shall survive termination.
+
+9. LIMITATION OF LIABILITY.
+
+     UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT
+     (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL
+     DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED CODE,
+     OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY PERSON FOR
+     ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES OF ANY
+     CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF GOODWILL,
+     WORK STOPPAGE, COMPUTER FAILURE OR MALFUNCTION, OR ANY AND ALL OTHER
+     COMMERCIAL DAMAGES OR LOSSES, EVEN IF SUCH PARTY SHALL HAVE BEEN
+     INFORMED OF THE POSSIBILITY OF SUCH DAMAGES. THIS LIMITATION OF
+     LIABILITY SHALL NOT APPLY TO LIABILITY FOR DEATH OR PERSONAL INJURY
+     RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE EXTENT APPLICABLE LAW
+     PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO NOT ALLOW THE
+     EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL DAMAGES, SO
+     THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU.
+
+10. U.S. GOVERNMENT END USERS.
+
+     The Covered Code is a "commercial item," as that term is defined in
+     48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer
+     software" and "commercial computer software documentation," as such
+     terms are used in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48
+     C.F.R. 12.212 and 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995),
+     all U.S. Government End Users acquire Covered Code with only those
+     rights set forth herein.
+
+11. MISCELLANEOUS.
+
+     This License represents the complete agreement concerning subject
+     matter hereof. If any provision of this License is held to be
+     unenforceable, such provision shall be reformed only to the extent
+     necessary to make it enforceable. This License shall be governed by
+     California law provisions (except to the extent applicable law, if
+     any, provides otherwise), excluding its conflict-of-law provisions.
+     With respect to disputes in which at least one party is a citizen of,
+     or an entity chartered or registered to do business in the United
+     States of America, any litigation relating to this License shall be
+     subject to the jurisdiction of the Federal Courts of the Northern
+     District of California, with venue lying in Santa Clara County,
+     California, with the losing party responsible for costs, including
+     without limitation, court costs and reasonable attorneys' fees and
+     expenses. The application of the United Nations Convention on
+     Contracts for the International Sale of Goods is expressly excluded.
+     Any law or regulation which provides that the language of a contract
+     shall be construed against the drafter shall not apply to this
+     License.
+
+12. RESPONSIBILITY FOR CLAIMS.
+
+     As between Initial Developer and the Contributors, each party is
+     responsible for claims and damages arising, directly or indirectly,
+     out of its utilization of rights under this License and You agree to
+     work with Initial Developer and Contributors to distribute such
+     responsibility on an equitable basis. Nothing herein is intended or
+     shall be deemed to constitute any admission of liability.
+
+13. MULTIPLE-LICENSED CODE.
+
+     Initial Developer may designate portions of the Covered Code as
+     "Multiple-Licensed".  "Multiple-Licensed" means that the Initial
+     Developer permits you to utilize portions of the Covered Code under
+     Your choice of the NPL or the alternative licenses, if any, specified
+     by the Initial Developer in the file described in Exhibit A.
+
+EXHIBIT A -Mozilla Public License.
+
+     ``The contents of this file are subject to the Mozilla Public License
+     Version 1.1 (the "License"); you may not use this file except in
+     compliance with the License. You may obtain a copy of the License at
+     http://www.mozilla.org/MPL/
+
+     Software distributed under the License is distributed on an "AS IS"
+     basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
+     License for the specific language governing rights and limitations
+     under the License.
+
+     The Original Code is ______________________________________.
+
+     The Initial Developer of the Original Code is ________________________.
+     Portions created by ______________________ are Copyright (C) ______
+     _______________________. All Rights Reserved.
+
+     Contributor(s): ______________________________________.
+
+     Alternatively, the contents of this file may be used under the terms
+     of the _____ license (the  "[___] License"), in which case the
+     provisions of [______] License are applicable instead of those
+     above.  If you wish to allow use of your version of this file only
+     under the terms of the [____] License and not to allow others to use
+     your version of this file under the MPL, indicate your decision by
+     deleting  the provisions above and replace  them with the notice and
+     other provisions required by the [___] License.  If you do not delete
+     the provisions above, a recipient may use your version of this file
+     under either the MPL or the [___] License."
+
+     [NOTE: The text of this Exhibit A may differ slightly from the text of
+     the notices in the Source Code files of the Original Code. You should
+     use the text of this Exhibit A rather than the text found in the
+     Original Code Source Code for Your Modifications.]
+
+### Microsoft Public License
+
+Microsoft Permissive License (Ms-PL)
+       This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software.
+1. Definitions
+
+       The terms \93reproduce,\94 \93reproduction,\94 \93derivative works,\94 and \93distribution\94 have the same meaning here as under U.S. copyright law.
+       A \93contribution\94 is the original software, or any additions or changes to the software.
+       A \93contributor\94 is any person that distributes its contribution under this license.
+        \93Licensed patents\94 are a contributor\92s patent claims that read directly on its contribution.
+2. Grant of Rights
+
+       (A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free copyright license to reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution or any derivative works that you create.
+       (B) Patent Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free license under its licensed patents to make, have made, use, sell, offer for sale, import, and/or otherwise dispose of its contribution in the software or derivative works of the contribution in the software.
+3. Conditions and Limitations
+
+       (A) No Trademark License- This license does not grant you rights to use any contributors\92 name, logo, or trademarks.
+       (B) If you bring a patent claim against any contributor over patents that you claim are infringed by the software, your patent license from such contributor to the software ends automatically.
+       (C) If you distribute any portion of the software, you must retain all copyright, patent, trademark, and attribution notices that are present in the software.
+       (D) If you distribute any portion of the software in source code form, you may do so only under this license by including a complete copy of this license with your distribution. If you distribute any portion of the software in compiled or object code form, you may only do so under a license that complies with this license.
+       (E) The software is licensed \93as-is.\94 You bear the risk of using it. The contributors give no express warranties, guarantees or conditions. You may have additional consumer rights under your local laws which this license cannot change. To the extent permitted under your local laws, the contributors exclude the implied warranties of merchantability, fitness for a particular purpose and non-infringement.
+       (F) If you distribute the software or derivative works with programs you develop, you agree to indemnify, defend, and hold harmless all contributors from any claims, including attorneys\92 fees, related to the distribution or use of your programs.  For clarity, you have no such obligations to a contributor for any claims based solely on the unmodified contributions of that contributor.
+       (G) If you make any additions or changes to the original software, you may only distribute them under a new namespace.  In addition, you will clearly identify your changes or additions as your own.
+
+### Infozip BSD
+
+This is version 2009-Jan-02 of the Info-ZIP license. The definitive
+version of this document should be available at
+ftp://ftp.info-zip.org/pub/infozip/license.html indefinitely and a
+copy at http://www.info-zip.org/pub/infozip/license.html.
+
+Copyright (c) 1990-2009 Info-ZIP. All rights reserved.
+
+For the purposes of this copyright and license, "Info-ZIP" is defined
+as the following set of individuals: Mark Adler, John Bush, Karl
+Davis, Harald Denker, Jean-Michel Dubois, Jean-loup Gailly, Hunter
+Goatley, Ed Gordon, Ian Gorman, Chris Herborth, Dirk Haase, Greg
+Hartwig, Robert Heath, Jonathan Hudson, Paul Kienitz, David
+Kirschbaum, Johnny Lee, Onno van der Linden, Igor Mandrichenko, Steve
+P. Miller, Sergio Monesi, Keith Owens, George Petrov, Greg Roelofs,
+Kai Uwe Rommel, Steve Salisbury, Dave Smith, Steven M. Schweda,
+Christian Spieler, Cosmin Truta, Antoine Verheijen, Paul von Behren,
+Rich Wales, Mike White.
+
+This software is provided "as is," without warranty of any kind,
+express or implied. In no event shall Info-ZIP or its contributors be
+held liable for any direct, indirect, incidental, special or
+consequential damages arising out of the use of or inability to use
+this software.
+
+Permission is granted to anyone to use this software for any purpose,
+including commercial applications, and to alter it and redistribute it
+freely, subject to the above disclaimer and the following
+restrictions:
+
+Redistributions of source code (in whole or in part) must retain the
+above copyright notice, definition, disclaimer, and this list of
+conditions.
+
+Redistributions in binary form (compiled executables and libraries)
+must reproduce the above copyright notice, definition, disclaimer, and
+this list of conditions in documentation and/or other materials
+provided with the distribution. Additional documentation is not needed
+for executables where a command line license option provides these and
+a note regarding this option is in the executable's startup
+banner. The sole exception to this condition is redistribution of a
+standard UnZipSFX binary (including SFXWiz) as part of a
+self-extracting archive; that is permitted without inclusion of this
+license, as long as the normal SFX banner has not been removed from
+the binary or disabled.
+
+Altered versions--including, but not limited to, ports to new
+operating systems, existing ports with new graphical interfaces,
+versions with modified or added functionality, and dynamic, shared, or
+static library versions not from Info-ZIP--must be plainly marked as
+such and must not be misrepresented as being the original source or,
+if binaries, compiled from the original source. Such altered versions
+also must not be misrepresented as being Info-ZIP releases--including,
+but not limited to, labeling of the altered versions with the names
+"Info-ZIP" (or any variation thereof, including, but not limited to,
+different capitalizations), "Pocket UnZip," "WiZ" or "MacZip" without
+the explicit permission of Info-ZIP. Such altered versions are further
+prohibited from misrepresentative use of the Zip-Bugs or Info-ZIP
+e-mail addresses or the Info-ZIP URL(s), such as to imply Info-ZIP
+will provide support for the altered versions.
+
+Info-ZIP retains the right to use the names "Info-ZIP," "Zip,"
+"UnZip," "UnZipSFX," "WiZ," "Pocket UnZip," "Pocket Zip," and "MacZip"
+for its own source and binary releases.
+
+### License Creative Commons 2.5
+
+// Copyright 2006 James Newton-King
+// http://www.newtonsoft.com
+//
+// This work is licensed under the Creative Commons Attribution 2.5 License
+// http://creativecommons.org/licenses/by/2.5/
+//
+// You are free:
+//    * to copy, distribute, display, and perform the work
+//    * to make derivative works
+//    * to make commercial use of the work
+//
+// Under the following conditions:
+//    * For any reuse or distribution, you must make clear to others the license terms of this work.
+//    * Any of these conditions can be waived if you get permission from the copyright holder.
+
+From: james.newtonking@gmail.com [mailto:james.newtonking@gmail.com] On Behalf Of James Newton-King
+Sent: Tuesday, June 05, 2007 6:36 AM
+To: Konstantin Triger
+Subject: Re: Support request by Konstantin Triger for Json.NET
+
+Hey Kosta
+
+I think it would be awesome to use Json.NET in Mono for System.Web.Extensions.
+
+The CC license has the following clause: Any of the above conditions can be waived if you get permission from the copyright holder.
+
+I can waive that statement for you and Mono. Would that be acceptable?
+
+
+Regards,
+James
+
+### Creative Commons Attribution 4.0 International Public License
+
+Attribution 4.0 International
+
+=======================================================================
+
+Creative Commons Corporation ("Creative Commons") is not a law firm and
+does not provide legal services or legal advice. Distribution of
+Creative Commons public licenses does not create a lawyer-client or
+other relationship. Creative Commons makes its licenses and related
+information available on an "as-is" basis. Creative Commons gives no
+warranties regarding its licenses, any material licensed under their
+terms and conditions, or any related information. Creative Commons
+disclaims all liability for damages resulting from their use to the
+fullest extent possible.
+
+Using Creative Commons Public Licenses
+
+Creative Commons public licenses provide a standard set of terms and
+conditions that creators and other rights holders may use to share
+original works of authorship and other material subject to copyright
+and certain other rights specified in the public license below. The
+following considerations are for informational purposes only, are not
+exhaustive, and do not form part of our licenses.
+
+     Considerations for licensors: Our public licenses are
+     intended for use by those authorized to give the public
+     permission to use material in ways otherwise restricted by
+     copyright and certain other rights. Our licenses are
+     irrevocable. Licensors should read and understand the terms
+     and conditions of the license they choose before applying it.
+     Licensors should also secure all rights necessary before
+     applying our licenses so that the public can reuse the
+     material as expected. Licensors should clearly mark any
+     material not subject to the license. This includes other CC-
+     licensed material, or material used under an exception or
+     limitation to copyright. More considerations for licensors:
+       wiki.creativecommons.org/Considerations_for_licensors
+
+     Considerations for the public: By using one of our public
+     licenses, a licensor grants the public permission to use the
+     licensed material under specified terms and conditions. If
+     the licensor's permission is not necessary for any reason--for
+     example, because of any applicable exception or limitation to
+     copyright--then that use is not regulated by the license. Our
+     licenses grant only permissions under copyright and certain
+     other rights that a licensor has authority to grant. Use of
+     the licensed material may still be restricted for other
+     reasons, including because others have copyright or other
+     rights in the material. A licensor may make special requests,
+     such as asking that all changes be marked or described.
+     Although not required by our licenses, you are encouraged to
+     respect those requests where reasonable. More_considerations
+     for the public: 
+       wiki.creativecommons.org/Considerations_for_licensees
+
+=======================================================================
+
+Creative Commons Attribution 4.0 International Public License
+
+By exercising the Licensed Rights (defined below), You accept and agree
+to be bound by the terms and conditions of this Creative Commons
+Attribution 4.0 International Public License ("Public License"). To the
+extent this Public License may be interpreted as a contract, You are
+granted the Licensed Rights in consideration of Your acceptance of
+these terms and conditions, and the Licensor grants You such rights in
+consideration of benefits the Licensor receives from making the
+Licensed Material available under these terms and conditions.
+
+
+Section 1 -- Definitions.
+
+  a. Adapted Material means material subject to Copyright and Similar
+     Rights that is derived from or based upon the Licensed Material
+     and in which the Licensed Material is translated, altered,
+     arranged, transformed, or otherwise modified in a manner requiring
+     permission under the Copyright and Similar Rights held by the
+     Licensor. For purposes of this Public License, where the Licensed
+     Material is a musical work, performance, or sound recording,
+     Adapted Material is always produced where the Licensed Material is
+     synched in timed relation with a moving image.
+
+  b. Adapter's License means the license You apply to Your Copyright
+     and Similar Rights in Your contributions to Adapted Material in
+     accordance with the terms and conditions of this Public License.
+
+  c. Copyright and Similar Rights means copyright and/or similar rights
+     closely related to copyright including, without limitation,
+     performance, broadcast, sound recording, and Sui Generis Database
+     Rights, without regard to how the rights are labeled or
+     categorized. For purposes of this Public License, the rights
+     specified in Section 2(b)(1)-(2) are not Copyright and Similar
+     Rights.
+
+  d. Effective Technological Measures means those measures that, in the
+     absence of proper authority, may not be circumvented under laws
+     fulfilling obligations under Article 11 of the WIPO Copyright
+     Treaty adopted on December 20, 1996, and/or similar international
+     agreements.
+
+  e. Exceptions and Limitations means fair use, fair dealing, and/or
+     any other exception or limitation to Copyright and Similar Rights
+     that applies to Your use of the Licensed Material.
+
+  f. Licensed Material means the artistic or literary work, database,
+     or other material to which the Licensor applied this Public
+     License.
+
+  g. Licensed Rights means the rights granted to You subject to the
+     terms and conditions of this Public License, which are limited to
+     all Copyright and Similar Rights that apply to Your use of the
+     Licensed Material and that the Licensor has authority to license.
+
+  h. Licensor means the individual(s) or entity(ies) granting rights
+     under this Public License.
+
+  i. Share means to provide material to the public by any means or
+     process that requires permission under the Licensed Rights, such
+     as reproduction, public display, public performance, distribution,
+     dissemination, communication, or importation, and to make material
+     available to the public including in ways that members of the
+     public may access the material from a place and at a time
+     individually chosen by them.
+
+  j. Sui Generis Database Rights means rights other than copyright
+     resulting from Directive 96/9/EC of the European Parliament and of
+     the Council of 11 March 1996 on the legal protection of databases,
+     as amended and/or succeeded, as well as other essentially
+     equivalent rights anywhere in the world.
+
+  k. You means the individual or entity exercising the Licensed Rights
+     under this Public License. Your has a corresponding meaning.
+
+
+Section 2 -- Scope.
+
+  a. License grant.
+
+       1. Subject to the terms and conditions of this Public License,
+          the Licensor hereby grants You a worldwide, royalty-free,
+          non-sublicensable, non-exclusive, irrevocable license to
+          exercise the Licensed Rights in the Licensed Material to:
+
+            a. reproduce and Share the Licensed Material, in whole or
+               in part; and
+
+            b. produce, reproduce, and Share Adapted Material.
+
+       2. Exceptions and Limitations. For the avoidance of doubt, where
+          Exceptions and Limitations apply to Your use, this Public
+          License does not apply, and You do not need to comply with
+          its terms and conditions.
+
+       3. Term. The term of this Public License is specified in Section
+          6(a).
+
+       4. Media and formats; technical modifications allowed. The
+          Licensor authorizes You to exercise the Licensed Rights in
+          all media and formats whether now known or hereafter created,
+          and to make technical modifications necessary to do so. The
+          Licensor waives and/or agrees not to assert any right or
+          authority to forbid You from making technical modifications
+          necessary to exercise the Licensed Rights, including
+          technical modifications necessary to circumvent Effective
+          Technological Measures. For purposes of this Public License,
+          simply making modifications authorized by this Section 2(a)
+          (4) never produces Adapted Material.
+
+       5. Downstream recipients.
+
+            a. Offer from the Licensor -- Licensed Material. Every
+               recipient of the Licensed Material automatically
+               receives an offer from the Licensor to exercise the
+               Licensed Rights under the terms and conditions of this
+               Public License.
+
+            b. No downstream restrictions. You may not offer or impose
+               any additional or different terms or conditions on, or
+               apply any Effective Technological Measures to, the
+               Licensed Material if doing so restricts exercise of the
+               Licensed Rights by any recipient of the Licensed
+               Material.
+
+       6. No endorsement. Nothing in this Public License constitutes or
+          may be construed as permission to assert or imply that You
+          are, or that Your use of the Licensed Material is, connected
+          with, or sponsored, endorsed, or granted official status by,
+          the Licensor or others designated to receive attribution as
+          provided in Section 3(a)(1)(A)(i).
+
+  b. Other rights.
+
+       1. Moral rights, such as the right of integrity, are not
+          licensed under this Public License, nor are publicity,
+          privacy, and/or other similar personality rights; however, to
+          the extent possible, the Licensor waives and/or agrees not to
+          assert any such rights held by the Licensor to the limited
+          extent necessary to allow You to exercise the Licensed
+          Rights, but not otherwise.
+
+       2. Patent and trademark rights are not licensed under this
+          Public License.
+
+       3. To the extent possible, the Licensor waives any right to
+          collect royalties from You for the exercise of the Licensed
+          Rights, whether directly or through a collecting society
+          under any voluntary or waivable statutory or compulsory
+          licensing scheme. In all other cases the Licensor expressly
+          reserves any right to collect such royalties.
+
+
+Section 3 -- License Conditions.
+
+Your exercise of the Licensed Rights is expressly made subject to the
+following conditions.
+
+  a. Attribution.
+
+       1. If You Share the Licensed Material (including in modified
+          form), You must:
+
+            a. retain the following if it is supplied by the Licensor
+               with the Licensed Material:
+
+                 i. identification of the creator(s) of the Licensed
+                    Material and any others designated to receive
+                    attribution, in any reasonable manner requested by
+                    the Licensor (including by pseudonym if
+                    designated);
+
+                ii. a copyright notice;
+
+               iii. a notice that refers to this Public License;
+
+                iv. a notice that refers to the disclaimer of
+                    warranties;
+
+                 v. a URI or hyperlink to the Licensed Material to the
+                    extent reasonably practicable;
+
+            b. indicate if You modified the Licensed Material and
+               retain an indication of any previous modifications; and
+
+            c. indicate the Licensed Material is licensed under this
+               Public License, and include the text of, or the URI or
+               hyperlink to, this Public License.
+
+       2. You may satisfy the conditions in Section 3(a)(1) in any
+          reasonable manner based on the medium, means, and context in
+          which You Share the Licensed Material. For example, it may be
+          reasonable to satisfy the conditions by providing a URI or
+          hyperlink to a resource that includes the required
+          information.
+
+       3. If requested by the Licensor, You must remove any of the
+          information required by Section 3(a)(1)(A) to the extent
+          reasonably practicable.
+
+       4. If You Share Adapted Material You produce, the Adapter's
+          License You apply must not prevent recipients of the Adapted
+          Material from complying with this Public License.
+
+
+Section 4 -- Sui Generis Database Rights.
+
+Where the Licensed Rights include Sui Generis Database Rights that
+apply to Your use of the Licensed Material:
+
+  a. for the avoidance of doubt, Section 2(a)(1) grants You the right
+     to extract, reuse, reproduce, and Share all or a substantial
+     portion of the contents of the database;
+
+  b. if You include all or a substantial portion of the database
+     contents in a database in which You have Sui Generis Database
+     Rights, then the database in which You have Sui Generis Database
+     Rights (but not its individual contents) is Adapted Material; and
+
+  c. You must comply with the conditions in Section 3(a) if You Share
+     all or a substantial portion of the contents of the database.
+
+For the avoidance of doubt, this Section 4 supplements and does not
+replace Your obligations under this Public License where the Licensed
+Rights include other Copyright and Similar Rights.
+
+
+Section 5 -- Disclaimer of Warranties and Limitation of Liability.
+
+  a. UNLESS OTHERWISE SEPARATELY UNDERTAKEN BY THE LICENSOR, TO THE
+     EXTENT POSSIBLE, THE LICENSOR OFFERS THE LICENSED MATERIAL AS-IS
+     AND AS-AVAILABLE, AND MAKES NO REPRESENTATIONS OR WARRANTIES OF
+     ANY KIND CONCERNING THE LICENSED MATERIAL, WHETHER EXPRESS,
+     IMPLIED, STATUTORY, OR OTHER. THIS INCLUDES, WITHOUT LIMITATION,
+     WARRANTIES OF TITLE, MERCHANTABILITY, FITNESS FOR A PARTICULAR
+     PURPOSE, NON-INFRINGEMENT, ABSENCE OF LATENT OR OTHER DEFECTS,
+     ACCURACY, OR THE PRESENCE OR ABSENCE OF ERRORS, WHETHER OR NOT
+     KNOWN OR DISCOVERABLE. WHERE DISCLAIMERS OF WARRANTIES ARE NOT
+     ALLOWED IN FULL OR IN PART, THIS DISCLAIMER MAY NOT APPLY TO YOU.
+
+  b. TO THE EXTENT POSSIBLE, IN NO EVENT WILL THE LICENSOR BE LIABLE
+     TO YOU ON ANY LEGAL THEORY (INCLUDING, WITHOUT LIMITATION,
+     NEGLIGENCE) OR OTHERWISE FOR ANY DIRECT, SPECIAL, INDIRECT,
+     INCIDENTAL, CONSEQUENTIAL, PUNITIVE, EXEMPLARY, OR OTHER LOSSES,
+     COSTS, EXPENSES, OR DAMAGES ARISING OUT OF THIS PUBLIC LICENSE OR
+     USE OF THE LICENSED MATERIAL, EVEN IF THE LICENSOR HAS BEEN
+     ADVISED OF THE POSSIBILITY OF SUCH LOSSES, COSTS, EXPENSES, OR
+     DAMAGES. WHERE A LIMITATION OF LIABILITY IS NOT ALLOWED IN FULL OR
+     IN PART, THIS LIMITATION MAY NOT APPLY TO YOU.
+
+  c. The disclaimer of warranties and limitation of liability provided
+     above shall be interpreted in a manner that, to the extent
+     possible, most closely approximates an absolute disclaimer and
+     waiver of all liability.
+
+
+Section 6 -- Term and Termination.
+
+  a. This Public License applies for the term of the Copyright and
+     Similar Rights licensed here. However, if You fail to comply with
+     this Public License, then Your rights under this Public License
+     terminate automatically.
+
+  b. Where Your right to use the Licensed Material has terminated under
+     Section 6(a), it reinstates:
+
+       1. automatically as of the date the violation is cured, provided
+          it is cured within 30 days of Your discovery of the
+          violation; or
+
+       2. upon express reinstatement by the Licensor.
+
+     For the avoidance of doubt, this Section 6(b) does not affect any
+     right the Licensor may have to seek remedies for Your violations
+     of this Public License.
+
+  c. For the avoidance of doubt, the Licensor may also offer the
+     Licensed Material under separate terms or conditions or stop
+     distributing the Licensed Material at any time; however, doing so
+     will not terminate this Public License.
+
+  d. Sections 1, 5, 6, 7, and 8 survive termination of this Public
+     License.
+
+
+Section 7 -- Other Terms and Conditions.
+
+  a. The Licensor shall not be bound by any additional or different
+     terms or conditions communicated by You unless expressly agreed.
+
+  b. Any arrangements, understandings, or agreements regarding the
+     Licensed Material not stated herein are separate from and
+     independent of the terms and conditions of this Public License.
+
+
+Section 8 -- Interpretation.
+
+  a. For the avoidance of doubt, this Public License does not, and
+     shall not be interpreted to, reduce, limit, restrict, or impose
+     conditions on any use of the Licensed Material that could lawfully
+     be made without permission under this Public License.
+
+  b. To the extent possible, if any provision of this Public License is
+     deemed unenforceable, it shall be automatically reformed to the
+     minimum extent necessary to make it enforceable. If the provision
+     cannot be reformed, it shall be severed from this Public License
+     without affecting the enforceability of the remaining terms and
+     conditions.
+
+  c. No term or condition of this Public License will be waived and no
+     failure to comply consented to unless expressly agreed to by the
+     Licensor.
+
+  d. Nothing in this Public License constitutes or may be interpreted
+     as a limitation upon, or waiver of, any privileges and immunities
+     that apply to the Licensor or You, including from the legal
+     processes of any jurisdiction or authority.
+
+
+=======================================================================
+
+Creative Commons is not a party to its public
+licenses. Notwithstanding, Creative Commons may elect to apply one of
+its public licenses to material it publishes and in those instances
+will be considered the “Licensor.” The text of the Creative Commons
+public licenses is dedicated to the public domain under the CC0 Public
+Domain Dedication. Except for the limited purpose of indicating that
+material is shared under a Creative Commons public license or as
+otherwise permitted by the Creative Commons policies published at
+creativecommons.org/policies, Creative Commons does not authorize the
+use of the trademark "Creative Commons" or any other trademark or logo
+of Creative Commons without its prior written consent including,
+without limitation, in connection with any unauthorized modifications
+to any of its public licenses or any other arrangements,
+understandings, or agreements concerning use of licensed material. For
+the avoidance of doubt, this paragraph does not form part of the
+public licenses.
+
+Creative Commons may be contacted at creativecommons.org.
+
+### GPL version 2
+
+                   GNU GENERAL PUBLIC LICENSE
+                      Version 2, June 1991
+
+ Copyright (C) 1989, 1991 Free Software Foundation, Inc.
+     59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ Everyone is permitted to copy and distribute verbatim copies
+ of this license document, but changing it is not allowed.
+
+                           Preamble
+
+  The licenses for most software are designed to take away your
+freedom to share and change it.  By contrast, the GNU General Public
+License is intended to guarantee your freedom to share and change free
+software--to make sure the software is free for all its users.  This
+General Public License applies to most of the Free Software
+Foundation's software and to any other program whose authors commit to
+using it.  (Some other Free Software Foundation software is covered by
+the GNU Library General Public License instead.)  You can apply it to
+your programs, too.
+
+  When we speak of free software, we are referring to freedom, not
+price.  Our General Public Licenses are designed to make sure that you
+have the freedom to distribute copies of free software (and charge for
+this service if you wish), that you receive source code or can get it
+if you want it, that you can change the software or use pieces of it
+in new free programs; and that you know you can do these things.
+
+  To protect your rights, we need to make restrictions that forbid
+anyone to deny you these rights or to ask you to surrender the rights.
+These restrictions translate to certain responsibilities for you if you
+distribute copies of the software, or if you modify it.
+
+  For example, if you distribute copies of such a program, whether
+gratis or for a fee, you must give the recipients all the rights that
+you have.  You must make sure that they, too, receive or can get the
+source code.  And you must show them these terms so they know their
+rights.
+
+  We protect your rights with two steps: (1) copyright the software, and
+(2) offer you this license which gives you legal permission to copy,
+distribute and/or modify the software.
+
+  Also, for each author's protection and ours, we want to make certain
+that everyone understands that there is no warranty for this free
+software.  If the software is modified by someone else and passed on, we
+want its recipients to know that what they have is not the original, so
+that any problems introduced by others will not reflect on the original
+authors' reputations.
+
+  Finally, any free program is threatened constantly by software
+patents.  We wish to avoid the danger that redistributors of a free
+program will individually obtain patent licenses, in effect making the
+program proprietary.  To prevent this, we have made it clear that any
+patent must be licensed for everyone's free use or not licensed at all.
+
+  The precise terms and conditions for copying, distribution and
+modification follow.
+\f
+                   GNU GENERAL PUBLIC LICENSE
+   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
+
+  0. This License applies to any program or other work which contains
+a notice placed by the copyright holder saying it may be distributed
+under the terms of this General Public License.  The "Program", below,
+refers to any such program or work, and a "work based on the Program"
+means either the Program or any derivative work under copyright law:
+that is to say, a work containing the Program or a portion of it,
+either verbatim or with modifications and/or translated into another
+language.  (Hereinafter, translation is included without limitation in
+the term "modification".)  Each licensee is addressed as "you".
+
+Activities other than copying, distribution and modification are not
+covered by this License; they are outside its scope.  The act of
+running the Program is not restricted, and the output from the Program
+is covered only if its contents constitute a work based on the
+Program (independent of having been made by running the Program).
+Whether that is true depends on what the Program does.
+
+  1. You may copy and distribute verbatim copies of the Program's
+source code as you receive it, in any medium, provided that you
+conspicuously and appropriately publish on each copy an appropriate
+copyright notice and disclaimer of warranty; keep intact all the
+notices that refer to this License and to the absence of any warranty;
+and give any other recipients of the Program a copy of this License
+along with the Program.
+
+You may charge a fee for the physical act of transferring a copy, and
+you may at your option offer warranty protection in exchange for a fee.
+
+  2. You may modify your copy or copies of the Program or any portion
+of it, thus forming a work based on the Program, and copy and
+distribute such modifications or work under the terms of Section 1
+above, provided that you also meet all of these conditions:
+
+    a) You must cause the modified files to carry prominent notices
+    stating that you changed the files and the date of any change.
+
+    b) You must cause any work that you distribute or publish, that in
+    whole or in part contains or is derived from the Program or any
+    part thereof, to be licensed as a whole at no charge to all third
+    parties under the terms of this License.
+
+    c) If the modified program normally reads commands interactively
+    when run, you must cause it, when started running for such
+    interactive use in the most ordinary way, to print or display an
+    announcement including an appropriate copyright notice and a
+    notice that there is no warranty (or else, saying that you provide
+    a warranty) and that users may redistribute the program under
+    these conditions, and telling the user how to view a copy of this
+    License.  (Exception: if the Program itself is interactive but
+    does not normally print such an announcement, your work based on
+    the Program is not required to print an announcement.)
+\f
+These requirements apply to the modified work as a whole.  If
+identifiable sections of that work are not derived from the Program,
+and can be reasonably considered independent and separate works in
+themselves, then this License, and its terms, do not apply to those
+sections when you distribute them as separate works.  But when you
+distribute the same sections as part of a whole which is a work based
+on the Program, the distribution of the whole must be on the terms of
+this License, whose permissions for other licensees extend to the
+entire whole, and thus to each and every part regardless of who wrote it.
+
+Thus, it is not the intent of this section to claim rights or contest
+your rights to work written entirely by you; rather, the intent is to
+exercise the right to control the distribution of derivative or
+collective works based on the Program.
+
+In addition, mere aggregation of another work not based on the Program
+with the Program (or with a work based on the Program) on a volume of
+a storage or distribution medium does not bring the other work under
+the scope of this License.
+
+  3. You may copy and distribute the Program (or a work based on it,
+under Section 2) in object code or executable form under the terms of
+Sections 1 and 2 above provided that you also do one of the following:
+
+    a) Accompany it with the complete corresponding machine-readable
+    source code, which must be distributed under the terms of Sections
+    1 and 2 above on a medium customarily used for software interchange; or,
+
+    b) Accompany it with a written offer, valid for at least three
+    years, to give any third party, for a charge no more than your
+    cost of physically performing source distribution, a complete
+    machine-readable copy of the corresponding source code, to be
+    distributed under the terms of Sections 1 and 2 above on a medium
+    customarily used for software interchange; or,
+
+    c) Accompany it with the information you received as to the offer
+    to distribute corresponding source code.  (This alternative is
+    allowed only for noncommercial distribution and only if you
+    received the program in object code or executable form with such
+    an offer, in accord with Subsection b above.)
+
+The source code for a work means the preferred form of the work for
+making modifications to it.  For an executable work, complete source
+code means all the source code for all modules it contains, plus any
+associated interface definition files, plus the scripts used to
+control compilation and installation of the executable.  However, as a
+special exception, the source code distributed need not include
+anything that is normally distributed (in either source or binary
+form) with the major components (compiler, kernel, and so on) of the
+operating system on which the executable runs, unless that component
+itself accompanies the executable.
+
+If distribution of executable or object code is made by offering
+access to copy from a designated place, then offering equivalent
+access to copy the source code from the same place counts as
+distribution of the source code, even though third parties are not
+compelled to copy the source along with the object code.
+\f
+  4. You may not copy, modify, sublicense, or distribute the Program
+except as expressly provided under this License.  Any attempt
+otherwise to copy, modify, sublicense or distribute the Program is
+void, and will automatically terminate your rights under this License.
+However, parties who have received copies, or rights, from you under
+this License will not have their licenses terminated so long as such
+parties remain in full compliance.
+
+  5. You are not required to accept this License, since you have not
+signed it.  However, nothing else grants you permission to modify or
+distribute the Program or its derivative works.  These actions are
+prohibited by law if you do not accept this License.  Therefore, by
+modifying or distributing the Program (or any work based on the
+Program), you indicate your acceptance of this License to do so, and
+all its terms and conditions for copying, distributing or modifying
+the Program or works based on it.
+
+  6. Each time you redistribute the Program (or any work based on the
+Program), the recipient automatically receives a license from the
+original licensor to copy, distribute or modify the Program subject to
+these terms and conditions.  You may not impose any further
+restrictions on the recipients' exercise of the rights granted herein.
+You are not responsible for enforcing compliance by third parties to
+this License.
+
+  7. If, as a consequence of a court judgment or allegation of patent
+infringement or for any other reason (not limited to patent issues),
+conditions are imposed on you (whether by court order, agreement or
+otherwise) that contradict the conditions of this License, they do not
+excuse you from the conditions of this License.  If you cannot
+distribute so as to satisfy simultaneously your obligations under this
+License and any other pertinent obligations, then as a consequence you
+may not distribute the Program at all.  For example, if a patent
+license would not permit royalty-free redistribution of the Program by
+all those who receive copies directly or indirectly through you, then
+the only way you could satisfy both it and this License would be to
+refrain entirely from distribution of the Program.
+
+If any portion of this section is held invalid or unenforceable under
+any particular circumstance, the balance of the section is intended to
+apply and the section as a whole is intended to apply in other
+circumstances.
+
+It is not the purpose of this section to induce you to infringe any
+patents or other property right claims or to contest validity of any
+such claims; this section has the sole purpose of protecting the
+integrity of the free software distribution system, which is
+implemented by public license practices.  Many people have made
+generous contributions to the wide range of software distributed
+through that system in reliance on consistent application of that
+system; it is up to the author/donor to decide if he or she is willing
+to distribute software through any other system and a licensee cannot
+impose that choice.
+
+This section is intended to make thoroughly clear what is believed to
+be a consequence of the rest of this License.
+\f
+  8. If the distribution and/or use of the Program is restricted in
+certain countries either by patents or by copyrighted interfaces, the
+original copyright holder who places the Program under this License
+may add an explicit geographical distribution limitation excluding
+those countries, so that distribution is permitted only in or among
+countries not thus excluded.  In such case, this License incorporates
+the limitation as if written in the body of this License.
+
+  9. The Free Software Foundation may publish revised and/or new versions
+of the General Public License from time to time.  Such new versions will
+be similar in spirit to the present version, but may differ in detail to
+address new problems or concerns.
+
+Each version is given a distinguishing version number.  If the Program
+specifies a version number of this License which applies to it and "any
+later version", you have the option of following the terms and conditions
+either of that version or of any later version published by the Free
+Software Foundation.  If the Program does not specify a version number of
+this License, you may choose any version ever published by the Free Software
+Foundation.
+
+  10. If you wish to incorporate parts of the Program into other free
+programs whose distribution conditions are different, write to the author
+to ask for permission.  For software which is copyrighted by the Free
+Software Foundation, write to the Free Software Foundation; we sometimes
+make exceptions for this.  Our decision will be guided by the two goals
+of preserving the free status of all derivatives of our free software and
+of promoting the sharing and reuse of software generally.
+
+                           NO WARRANTY
+
+  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
+FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN
+OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
+PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
+OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
+MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS
+TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE
+PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
+REPAIR OR CORRECTION.
+
+  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
+WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
+REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
+INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
+OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
+TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
+YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
+PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
+POSSIBILITY OF SUCH DAMAGES.
+
+                    END OF TERMS AND CONDITIONS
+\f
+           How to Apply These Terms to Your New Programs
+
+  If you develop a new program, and you want it to be of the greatest
+possible use to the public, the best way to achieve this is to make it
+free software which everyone can redistribute and change under these terms.
+
+  To do so, attach the following notices to the program.  It is safest
+to attach them to the start of each source file to most effectively
+convey the exclusion of warranty; and each file should have at least
+the "copyright" line and a pointer to where the full notice is found.
+
+    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) <year>  <name of author>
+
+    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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+
+
+Also add information on how to contact you by electronic and paper mail.
+
+If the program is interactive, make it output a short notice like this
+when it starts in an interactive mode:
+
+    Gnomovision version 69, Copyright (C) year  name of author
+    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+The hypothetical commands `show w' and `show c' should show the appropriate
+parts of the General Public License.  Of course, the commands you use may
+be called something other than `show w' and `show c'; they could even be
+mouse-clicks or menu items--whatever suits your program.
+
+You should also get your employer (if you work as a programmer) or your
+school, if any, to sign a "copyright disclaimer" for the program, if
+necessary.  Here is a sample; alter the names:
+
+  Yoyodyne, Inc., hereby disclaims all copyright interest in the program
+  `Gnomovision' (which makes passes at compilers) written by James Hacker.
 
-        GNU GPL: details avaliable in the file mcs/LICENSE.GPL
-        GNU LGPL: details available in the file mcs/LICENSE.LGPL
-        MIT X11: text available in the file mcs/MIT.X11
-        MPL: text available in the file mcs/LICENSE.MPL
+  <signature of Ty Coon>, 1 April 1989
+  Ty Coon, President of Vice
 
+This General Public License does not permit incorporating your program into
+proprietary programs.  If your program is a subroutine library, you may
+consider it more useful to permit linking proprietary applications with the
+library.  If this is what you want to do, use the GNU Library General
+Public License instead of this License.
diff --git a/PATENTS.TXT b/PATENTS.TXT
new file mode 100644 (file)
index 0000000..a868428
--- /dev/null
@@ -0,0 +1,44 @@
+Microsoft Patent Promise for Mono
+
+Microsoft Corporation and its affiliates (“Microsoft”) promise not to
+assert any Applicable Patents against you for making, using, selling,
+offering for sale, importing, or distributing Mono.
+
+If you file, maintain, or voluntarily participate in any claim in a
+lawsuit alleging direct or contributory patent infringement by Mono,
+or inducement of patent infringement by Mono, then your rights under
+this promise will automatically terminate.
+
+This promise is not an assurance that (i) any Applicable Patents are
+valid or enforceable or (ii) Mono does not infringe patents or other
+intellectual property rights of any third party. No rights except
+those expressly stated in this promise are granted, waived or received
+by Microsoft, whether by implication, exhaustion, estoppel or
+otherwise. This is a personal promise directly from Microsoft to you,
+and you agree as a condition of benefitting from it that no Microsoft
+rights are received from suppliers, distributors, or otherwise in
+connection with this promise.
+
+Definitions:
+
+“Mono” means those portions of the software development technology, as
+originally distributed by Xamarin, Inc. or the .NET Foundation under
+the name “Mono,” that implement .NET Framework Functionality, provided
+that such portions at a minimum implement all of the required parts of
+the mandatory provisions of Standard ECMA-335 – Common Language
+Infrastructure (CLI).
+
+“.NET Framework Functionality” means any functionality in Microsoft’s
+.NET Framework as described in Microsoft’s API documentation on
+Microsoft’s MSDN website, including the functionality in
+Windowsbase.dll, but excluding all other functionality in the Windows
+Presentation Foundation component of .NET Framework.
+
+“Applicable Patents” are those patent claims, currently owned by
+Microsoft and acquired in the future, that are necessarily infringed
+by Mono. For clarity, Applicable Patents do not include any patent
+claims that are infringed (x) by any underlying or enabling technology
+that may be used, combined, or distributed in connection with Mono
+(such as hardware, operating systems, or applications that run on
+Mono), (y) only as a consequence of modification of Mono, or (z) only
+by the combination of Mono with third party code.
index 7a7f3639f28ccefebc994e5d5f03cb0ae41f2ce1..5aad9440a06112eb34bb89a82f8bd46fb2910640 100644 (file)
--- a/README.md
+++ b/README.md
@@ -3,6 +3,8 @@ create cross platform applications.  It is an open source
 implementation of Microsoft's .NET Framework based on the ECMA
 standards for C# and the Common Language Runtime.
 
+The Mono project is part of the [.NET Foundation](http://www.dotnetfoundation.org/)
+
 [![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/mono/mono?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
 
 1. [Compilation and Installation](#compilation-and-installation)
@@ -104,6 +106,8 @@ See the man pages for mono(1), mcs(1) and monodis(1) for further details.
 Directory Roadmap
 =================
 
+* `acceptance-tests/` - Optional third party test suites used to validate Mono against a wider range of test cases.
+
 * `data/` - Configuration files installed as part of the Mono runtime.
 
 * `docs/` - Technical documents about the Mono runtime.
@@ -505,3 +509,15 @@ to do at all), first edit `.gitmodules` to point to the new location, then:
 The desired output diff is a change in `.gitmodules` to reflect the
 change in the remote URL, and a change in /<submodule> where you see
 the desired change in the commit hash.
+
+License
+=======
+
+See the LICENSE file for licensing information, and the PATENTS.TXT
+file for information about Microsoft's patent grant.
+
+Mono Trademark Use Policy
+=======
+
+The use of trademarks and logos for Mono can be found [here] (http://www.dotnetfoundation.org/legal/mono-tm). 
+
index 7a9de16bc374515f3f926267bfcfc27645a232cd..2e83f9ea795adc63dd194c6b713d067287d871d4 100644 (file)
@@ -10,7 +10,7 @@
   {
     "name": "coreclr", 
     "url": "git://github.com/mono/coreclr.git", 
-    "rev": "3d9a68d3baaa32df28b70a2266a9ef9ee2176b79", 
+    "rev": "b05c242a59eab1c4ea2803960c8065167308546d", 
     "remote-branch": "origin/mono", 
     "branch": "mono", 
     "directory": "coreclr"
index 2271e371f6906a8ef575697b7ab23057ab51dd04..8f75b05470fe46685d232f3a35933dbc1080fc59 100644 (file)
@@ -5152,7 +5152,7 @@ $(CORECLR_PATH)%.exe: $(CORECLR_PATH)%.cs coreclr-testlibrary.dll
        $(MCS) -unsafe -debug -nowarn:0162 -nowarn:0168 -nowarn:0219 -nowarn:0414 -nowarn:0618 -nowarn:0169 -nowarn:1690 -nowarn:0649 -nowarn:0612 -nowarn:3021 -nowarn:0197 -r:coreclr-testlibrary.dll -d:MONO -out:$@ $<
 
 test-runner.exe: $(top_srcdir)/mono/tests/test-runner.cs
-       $(MCS) -debug -out:$@ $<
+       $(MCS) -debug -r:Mono.Posix.dll -out:$@ $<
 
 GCStressTests.exe: $(CORECLR_STRESSTEST_RUNNER_CS_SRC)
        $(MCS) -out:$@ -debug -d:PROJECTK_BUILD $(CORECLR_STRESSTEST_RUNNER_CS_SRC)
index 17e0e4ce67580a5f3a762dbd89ca5d8bb8ab667f..fbfa2760ec2744588adbfb251e67a2a4adf3ae23 100644 (file)
@@ -10,7 +10,7 @@ check-roslyn:
                mkdir -p $$MONO_DOTNET_PORTABLE_DIR; \
                mkdir -p $$MONO_NUGET_TARGETS_DIR; \
                mkdir -p $$MONO_PORTABLE_TARGETS_DIR; \
-               curl -SL "http://storage.bos.internalx.com/bot-provisioning/RoslynBuildDependencies.zip" > /tmp/RoslynBuildDependencies.zip; \
+               curl -SL "http://download.mono-project.com/third-party/RoslynBuildDependencies.zip" > /tmp/RoslynBuildDependencies.zip; \
                unzip -o /tmp/RoslynBuildDependencies.zip -d /tmp/RoslynBuildDependencies; \
                cp -r /tmp/RoslynBuildDependencies/PortableReferenceAssemblies/* $$MONO_DOTNET_PORTABLE_DIR; \
                cp /tmp/RoslynBuildDependencies/NuGetTargets/* $$MONO_NUGET_TARGETS_DIR; \
index 5fff4f18f38bbeb6b374cdfbb5fd672568fb54de..35ded0c0fcd74c3aa017682864890a6e501c885c 100755 (executable)
@@ -8,12 +8,12 @@ def find_module(submodules, name):
         if item["name"] == name:
             return item
 
-    print "Not found"
+    print("Not found")
     sys.exit(1)
 
 
 if len(sys.argv) < 2:
-    print "Usage: versions.py <command>"
+    print("Usage: versions.py <command>")
     sys.exit(1)
 
 CONFIG_FILE = "SUBMODULES.json"
@@ -23,16 +23,16 @@ submodules = json.load(open(CONFIG_FILE))
 
 if command == "get-rev":
     mod = find_module(submodules, sys.argv[2])
-    print mod["rev"]
+    print(mod["rev"])
 elif command == "get-url":
     mod = find_module(submodules, sys.argv[2])
-    print mod["url"]
+    print(mod["url"])
 elif command == "get-dir":
     mod = find_module(submodules, sys.argv[2])
-    print mod["directory"]
+    print(mod["directory"])
 elif command == "get-remote-branch":
     mod = find_module(submodules, sys.argv[2])
-    print mod["remote-branch"]
+    print(mod["remote-branch"])
 elif command == "set-rev":
     mod = find_module(submodules, sys.argv[2])
     mod["rev"] = sys.argv[3]
@@ -46,7 +46,7 @@ elif command == "set-remote-branch":
     mod["remote-branch"] = sys.argv[3]
     json.dump(submodules, open(CONFIG_FILE, "w"), indent = 2)
 elif command == "cat":
-    print json.dumps(submodules, indent = 2)
+    print(json.dumps(submodules, indent = 2))
 else:
-    print "Unknown command "" + command + ""."
+    print("Unknown command "" + command + "".")
     sys.exit(1)
index bf0e910961bee936d8a8ccaea91b02d2472813ae..966bd50391504aa8e884de27ef4bbf2fe058645e 100644 (file)
@@ -1,7 +1,7 @@
 # Process this file with autoconf to produce a configure script.
 #AC_PREREQ([2.62])
 
-AC_INIT(mono, [4.5.0],
+AC_INIT(mono, [4.5.1],
         [http://bugzilla.xamarin.com/enter_bug.cgi?classification=Mono])
 
 AC_CONFIG_SRCDIR([README.md])
@@ -92,11 +92,11 @@ case "$host" in
                host_win32=yes
                mono_cv_clang=no
                if test "x$cross_compiling" = "xno"; then
-                       if test "x$host" == "x$build" -a "x$host" == "x$target"; then
+                       if test "x$host" = "x$build" -a "x$host" = "x$target"; then
                                target_win32=yes
                        fi
                else
-                       if test "x$host" == "x$target"; then
+                       if test "x$host" = "x$target"; then
                                target_win32=yes
                        fi
                fi
@@ -272,8 +272,6 @@ case "$host" in
                need_link_unlink=yes
                libmono_cflags="-D_REENTRANT"
                libgc_threads=pthreads
-               # This doesn't seem to work on solaris/x86, but the configure test runs
-               with_tls=pthread
                has_dtrace=yes
                use_sigposix=yes
                enable_solaris_tar_check=yes
@@ -929,15 +927,8 @@ if test x$has_extension_module != xno ; then
        AC_MSG_NOTICE([Enabling mono extension module.])
 fi
 
-AC_ARG_ENABLE(gsharedvt, [  --enable-gsharedvt Enable generic valuetype sharing], enable_gsharedvt=$enableval, enable_gsharedvt=no)
-if test x$enable_gsharedvt = xyes; then
-       AC_DEFINE(ENABLE_GSHAREDVT,1,[Gsharedvt])
-fi
-
-AC_ARG_ENABLE(native-types, [  --enable-native-types Enable native types], enable_native_types=$enableval, enable_native_types=no)
-if test x$enable_native_types = xyes; then
-       AC_DEFINE(MONO_NATIVE_TYPES,1,[native types])
-fi
+# Deprecated
+AC_ARG_ENABLE(gsharedvt, [  --enable-gsharedvt Enable generic valuetype sharing (Deprecated)], enable_gsharedvt=$enableval, enable_gsharedvt=no)
 
 AC_MSG_CHECKING(for visibility __attribute__)
 AC_COMPILE_IFELSE([
@@ -1083,6 +1074,7 @@ if test x$host_win32 = xno; then
 
        dnl hires monotonic clock support
        AC_SEARCH_LIBS(clock_gettime, rt)
+       AC_CHECK_FUNCS(clock_nanosleep)
 
        dnl dynamic loader support
        AC_CHECK_FUNC(dlopen, DL_LIB="",
@@ -2324,6 +2316,9 @@ else
                #include <winsock2.h>
                #include <ws2tcpip.h>
        ], [
+               #ifndef inet_pton
+               (void) inet_pton;
+               #endif
                inet_pton (0, NULL, NULL);
        ], [
                # Yes, we have it...
@@ -2456,7 +2451,7 @@ fi
 AC_ARG_ENABLE(bcl-opt, [  --disable-bcl-opt    BCL is compiled with no optimizations (allows accurate BCL debugging)], test_bcl_opt=$enableval, test_bcl_opt=yes)
 
 AC_ARG_ENABLE(perf-events, [  --enable-perf-events Enable using `perf` for profiling on Linux], test_perf_events=$enableval, test_perf_events=no)
-if test "x$test_perf_events" == "xyes"; then
+if test "x$test_perf_events" = "xyes"; then
        AC_DEFINE(ENABLE_PERF_EVENTS, 1, [Enable using `perf` for profiling on Linux])
        AC_SUBST(ENABLE_PERF_EVENTS)
 fi
@@ -2618,7 +2613,7 @@ if test "x$enable_llvm" = "xyes"; then
    AC_MSG_CHECKING(LLVM version)
    AC_MSG_RESULT($llvm_version $llvm_api_version)
    if echo $llvm_version | grep -q 'mono'; then
-         if test "x$enable_llvm_version_check" == "xyes"; then
+         if test "x$enable_llvm_version_check" = "xyes"; then
                 if test "$llvm_version" != "$expected_llvm_version"; then
                        AC_MSG_ERROR([Expected llvm version $expected_llvm_version, but llvm-config --version returned $llvm_version"])
                 fi
@@ -2653,7 +2648,7 @@ if test "x$enable_llvm" = "xyes"; then
       llvm_jit_libs=""
    fi
    LLVM_LIBS=`$LLVM_CONFIG --libs analysis core bitwriter $llvm_jit_libs`
-   if test "x$LLVM_LIBS" == "x"; then
+   if test "x$LLVM_LIBS" = "x"; then
          echo "$LLVM_CONFIG --libs failed."
          exit 1
    fi
@@ -2895,6 +2890,12 @@ case "$host" in
                AOT_SUPPORTED="yes"
                CPPFLAGS="$CPPFLAGS -D__ARM_EABI__"
                ;;
+       arm*-netbsd*-eabi*)
+               TARGET=ARM;
+               arch_target=arm;
+               ACCESS_UNALIGNED="no"
+               CPPFLAGS="$CPPFLAGS -D__ARM_EABI__"
+               ;;
 # TODO: make proper support for NaCl host.
 #        arm*-*nacl)
 #              TARGET=ARM;
@@ -3009,6 +3010,17 @@ if test "x$host" != "x$target"; then
                        ;;
                esac
                ;;
+   arm*-netbsd*-eabi*)
+               TARGET=ARM;
+               arch_target=arm;
+               AC_DEFINE(TARGET_ARM, 1, [...])
+               ACCESS_UNALIGNED="no"
+               CPPFLAGS="$CPPFLAGS -D__ARM_EABI__"
+               # Can't use tls, since it depends on the runtime detection of tls offsets
+               # in mono-compiler.h
+               with_tls=pthread
+               target_mach=no
+               ;;
    i686*-linux-*)
                TARGET=X86;
                arch_target=x86;
@@ -3270,8 +3282,10 @@ case "$host" in
        GTKX11="libgtk-x11-2.0.dylib"
        ;;
      *-*-*netbsd*)
-       LIBC="libc.so.12"
-       INTL="libintl.so.0"
+       LIBC="libc.so"
+       INTL="libintl.so"
+       SQLITE="libsqlite.so"
+       SQLITE3="libsqlite3.so"
        ;;
      *-*-kfreebsd*-gnu)
        LIBC="libc.so.0.1"
@@ -3319,6 +3333,12 @@ AC_ARG_WITH([libgdiplus],
 
 # default install location
 libgdiplus_install_loc=libgdiplus${libsuffix}
+case "$host" in
+    *-*-*linux*)
+    libgdiplus_install_loc=libgdiplus${libsuffix}.0
+    ;;
+esac
+
 case $with_libgdiplus in
     no|installed)
     libgdiplus_loc=
@@ -3583,35 +3603,34 @@ AC_ARG_WITH(cooperative_gc, [  --with-cooperative-gc=yes|no      Enable cooperat
        fi
 ], [with_cooperative_gc=no])
 
-AC_ARG_WITH(checked_build, [  --with-checked-build=yes|no      Enable checked build (expensive asserts)) (defaults to no)],[
-       if test x$with_checked_build != xno ; then
-               AC_DEFINE(CHECKED_BUILD,1,[Enable checked build.])
-       fi
-], [with_checked_build=no])
+AC_ARG_ENABLE(checked_build, [  --enable-checked-build=LIST      To enable checked build (expensive asserts), configure with a comma-separated LIST of checked build modules and then include that same list in the environment variable MONO_CHECK_MODE at runtime. Recognized checked build modules: all, gc, metadata, thread],[
 
-if test x$with_checked_build != xno ; then
-       DISABLED_CHECKED_BUILD_TEST=none
+       if test x$enable_checked_build != x ; then
+               AC_DEFINE(ENABLE_CHECKED_BUILD,1,[Enable checked build])
+       fi
+       for feature in `echo "$enable_checked_build" | sed -e "s/,/ /g"`; do
+               eval "mono_checked_build_test_enable_$feature='yes'"
+       done
 
-       AC_ARG_ENABLE(checked_build_test, [  --enable-checked-build-test=LIST      drop support for LIST checked build tests. LIST is a comma-separated list from: gc, metadata, thread.],
-       [
-               for feature in `echo "$enable_checked_build_test" | sed -e "s/,/ /g"`; do
-                       eval "mono_checked_build_test_disable_$feature='yes'"
-               done
-               DISABLED_CHECKED_BUILD_TEST=$enable_checked_build_test
-       ],[])
+       if test "x$mono_checked_build_test_enable_all" = "xyes"; then
+               eval "mono_checked_build_test_enable_gc='yes'"
+               eval "mono_checked_build_test_enable_metadata='yes'"
+               eval "mono_checked_build_test_enable_thread='yes'"
+       fi
 
-       if test "x$mono_checked_build_test_disable_gc" = "xyes"; then
-               AC_DEFINE(DISABLE_CHECKED_BUILD_GC, 1, [Disable GC checked build])
+       if test "x$mono_checked_build_test_enable_gc" = "xyes"; then
+               AC_DEFINE(ENABLE_CHECKED_BUILD_GC, 1, [Enable GC checked build])
        fi
 
-       if test "x$mono_checked_build_test_disable_metadata" = "xyes"; then
-               AC_DEFINE(DISABLE_CHECKED_BUILD_METADATA, 1, [Disable metadata checked build])
+       if test "x$mono_checked_build_test_enable_metadata" = "xyes"; then
+               AC_DEFINE(ENABLE_CHECKED_BUILD_METADATA, 1, [Enable metadata checked build])
        fi
 
-       if test "x$mono_checked_build_test_disable_thread" = "xyes"; then
-               AC_DEFINE(DISABLE_CHECKED_BUILD_THREAD, 1, [Disable thread checked build])
+       if test "x$mono_checked_build_test_enable_thread" = "xyes"; then
+               AC_DEFINE(ENABLE_CHECKED_BUILD_THREAD, 1, [Enable thread checked build])
        fi
-fi
+
+], [])
 
 AC_CHECK_HEADER([malloc.h], 
                [AC_DEFINE([HAVE_USR_INCLUDE_MALLOC_H], [1], 
@@ -4064,10 +4083,6 @@ fi
     if test x$has_extension_module != xno; then
         echo "EXTENSION_MODULE = 1" >> $srcdir/$mcsdir/build/config.make
     fi
-
-    if test x$enable_gsharedvt = xno; then
-        echo "MONO_DISABLE_GSHAREDVT = 1" >> $srcdir/$mcsdir/build/config.make
-    fi
     
     echo "DEFAULT_PROFILE = $default_profile" >> $srcdir/$mcsdir/build/config.make
     
index c19ba5c33758cc2e935f459b907e8b3d22736a4a..f0b979903569b952d3875075a7af57206fc7f124 100644 (file)
@@ -13,10 +13,10 @@ ASSEMBLED_DOCS = \
        monoapi.tree monoapi.zip
 
 convert.exe: $(srcdir)/convert.cs AgilityPack.dll
-       $(CSCOMPILE) -r:System.Xml.dll -out:$@ $< -r:AgilityPack.dll
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Xml.dll -out:$@ $< -r:AgilityPack.dll
 
 AgilityPack.dll:
-       $(CSCOMPILE) -r:System.dll -r:System.Xml.dll -target:library -out:$@ $(srcdir)/HtmlAgilityPack/*.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.dll -r:$(topdir)/class/lib/$(PROFILE)/System.Xml.dll -target:library -out:$@ $(srcdir)/HtmlAgilityPack/*.cs
 
 monoapi.zip: monoapi.tree
        @test -f $@ || { rm -f $< && $(MAKE) $<; }
diff --git a/external/android-libunwind/README b/external/android-libunwind/README
new file mode 100644 (file)
index 0000000..b226141
--- /dev/null
@@ -0,0 +1,9 @@
+This is a copy of a few libunwind headers from https://android.googlesource.com/platform/external/libunwind
+
+We can't make the repo a git submodule because it contains a folder called 'aux' which
+is reserved on Windows and would break on checkout there.
+
+These files are unmodified from the originals and should preferably stay that
+way to avoid merge hell.
+
+Commit: 338c9755cfe3d009c3dfff7d108e2c3ddaa6f3bb (android-6.0.1_r24)
\ No newline at end of file
diff --git a/external/android-libunwind/include/libunwind-aarch64.h b/external/android-libunwind/include/libunwind-aarch64.h
new file mode 100644 (file)
index 0000000..700ed17
--- /dev/null
@@ -0,0 +1,219 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2001-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+   Copyright (C) 2013 Linaro Limited
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <stddef.h>
+#include <ucontext.h>
+
+#define UNW_TARGET     aarch64
+#define UNW_TARGET_AARCH64     1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+
+#define UNW_TDEP_CURSOR_LEN    4096
+
+typedef uint64_t unw_word_t;
+typedef int64_t unw_sword_t;
+
+typedef long double unw_tdep_fpreg_t;
+
+typedef struct
+  {
+    /* no aarch64-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+typedef enum
+  {
+    /* 64-bit general registers.  */
+    UNW_AARCH64_X0,
+    UNW_AARCH64_X1,
+    UNW_AARCH64_X2,
+    UNW_AARCH64_X3,
+    UNW_AARCH64_X4,
+    UNW_AARCH64_X5,
+    UNW_AARCH64_X6,
+    UNW_AARCH64_X7,
+    UNW_AARCH64_X8,
+
+    /* Temporary registers.  */
+    UNW_AARCH64_X9,
+    UNW_AARCH64_X10,
+    UNW_AARCH64_X11,
+    UNW_AARCH64_X12,
+    UNW_AARCH64_X13,
+    UNW_AARCH64_X14,
+    UNW_AARCH64_X15,
+
+    /* Intra-procedure-call temporary registers.  */
+    UNW_AARCH64_X16,
+    UNW_AARCH64_X17,
+
+    /* Callee-saved registers.  */
+    UNW_AARCH64_X18,
+    UNW_AARCH64_X19,
+    UNW_AARCH64_X20,
+    UNW_AARCH64_X21,
+    UNW_AARCH64_X22,
+    UNW_AARCH64_X23,
+    UNW_AARCH64_X24,
+    UNW_AARCH64_X25,
+    UNW_AARCH64_X26,
+    UNW_AARCH64_X27,
+    UNW_AARCH64_X28,
+
+    /* 64-bit frame pointer.  */
+    UNW_AARCH64_X29,
+
+    /* 64-bit link register.  */
+    UNW_AARCH64_X30,
+
+    /* 64-bit stack pointer.  */
+    UNW_AARCH64_SP =  31,
+    UNW_AARCH64_PC,
+    UNW_AARCH64_PSTATE,
+
+    /* 128-bit FP/Advanced SIMD registers.  */
+    UNW_AARCH64_V0 = 64,
+    UNW_AARCH64_V1,
+    UNW_AARCH64_V2,
+    UNW_AARCH64_V3,
+    UNW_AARCH64_V4,
+    UNW_AARCH64_V5,
+    UNW_AARCH64_V6,
+    UNW_AARCH64_V7,
+    UNW_AARCH64_V8,
+    UNW_AARCH64_V9,
+    UNW_AARCH64_V10,
+    UNW_AARCH64_V11,
+    UNW_AARCH64_V12,
+    UNW_AARCH64_V13,
+    UNW_AARCH64_V14,
+    UNW_AARCH64_V15,
+    UNW_AARCH64_V16,
+    UNW_AARCH64_V17,
+    UNW_AARCH64_V18,
+    UNW_AARCH64_V19,
+    UNW_AARCH64_V20,
+    UNW_AARCH64_V21,
+    UNW_AARCH64_V22,
+    UNW_AARCH64_V23,
+    UNW_AARCH64_V24,
+    UNW_AARCH64_V25,
+    UNW_AARCH64_V26,
+    UNW_AARCH64_V27,
+    UNW_AARCH64_V28,
+    UNW_AARCH64_V29,
+    UNW_AARCH64_V30,
+    UNW_AARCH64_V31,
+
+    UNW_AARCH64_FPSR,
+    UNW_AARCH64_FPCR,
+
+    /* For AArch64, the CFA is the value of SP (x31) at the call site of the
+       previous frame.  */
+    UNW_AARCH64_CFA = UNW_AARCH64_SP,
+
+    UNW_TDEP_LAST_REG = UNW_AARCH64_FPCR,
+
+    UNW_TDEP_IP = UNW_AARCH64_X30,
+    UNW_TDEP_SP = UNW_AARCH64_SP,
+    UNW_TDEP_EH = UNW_AARCH64_X0,
+
+  }
+aarch64_regnum_t;
+
+/* Use R0 through R3 to pass exception handling information.  */
+#define UNW_TDEP_NUM_EH_REGS   4
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+
+/* On AArch64, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+#include "libunwind-common.h"
+#include "libunwind-dynamic.h"
+
+/* ANDROID support update. */
+/* There is no getcontext in Android. */
+#define unw_tdep_getcontext(uc) (({                                    \
+  unw_tdep_context_t *unw_ctx = (uc);                                  \
+  register uint64_t *unw_base asm ("x0") = (uint64_t*) unw_ctx->uc_mcontext.regs;              \
+  __asm__ __volatile__ (                                               \
+     "stp x0, x1, [%[base], #0]\n" \
+     "stp x2, x3, [%[base], #16]\n" \
+     "stp x4, x5, [%[base], #32]\n" \
+     "stp x6, x7, [%[base], #48]\n" \
+     "stp x8, x9, [%[base], #64]\n" \
+     "stp x10, x11, [%[base], #80]\n" \
+     "stp x12, x13, [%[base], #96]\n" \
+     "stp x14, x13, [%[base], #112]\n" \
+     "stp x16, x17, [%[base], #128]\n" \
+     "stp x18, x19, [%[base], #144]\n" \
+     "stp x20, x21, [%[base], #160]\n" \
+     "stp x22, x23, [%[base], #176]\n" \
+     "stp x24, x25, [%[base], #192]\n" \
+     "stp x26, x27, [%[base], #208]\n" \
+     "stp x28, x29, [%[base], #224]\n" \
+     "str x30, [%[base], #240]\n" \
+     "mov x1, sp\n" \
+     "stp x1, x30, [%[base], #248]\n" \
+     : [base] "+r" (unw_base) : : "x1", "memory"); \
+  }), 0)
+/* End of ANDROID update. */
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-arm.h b/external/android-libunwind/include/libunwind-arm.h
new file mode 100644 (file)
index 0000000..495948e
--- /dev/null
@@ -0,0 +1,308 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2008 CodeSourcery
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <stddef.h>
+
+#define UNW_TARGET     arm
+#define UNW_TARGET_ARM 1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+   
+/* FIXME for ARM. Too big?  What do other things use for similar tasks?  */
+#define UNW_TDEP_CURSOR_LEN    4096
+
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+
+typedef long double unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    UNW_ARM_R0,
+    UNW_ARM_R1,
+    UNW_ARM_R2,
+    UNW_ARM_R3,
+    UNW_ARM_R4,
+    UNW_ARM_R5,
+    UNW_ARM_R6,
+    UNW_ARM_R7,
+    UNW_ARM_R8,
+    UNW_ARM_R9,
+    UNW_ARM_R10,
+    UNW_ARM_R11,
+    UNW_ARM_R12,
+    UNW_ARM_R13,
+    UNW_ARM_R14,
+    UNW_ARM_R15,
+    
+    /* VFPv2 s0-s31 (obsolescent numberings).  */
+    UNW_ARM_S0 = 64,
+    UNW_ARM_S1,
+    UNW_ARM_S2,
+    UNW_ARM_S3,
+    UNW_ARM_S4,
+    UNW_ARM_S5,
+    UNW_ARM_S6,
+    UNW_ARM_S7,
+    UNW_ARM_S8,
+    UNW_ARM_S9,
+    UNW_ARM_S10,
+    UNW_ARM_S11,
+    UNW_ARM_S12,
+    UNW_ARM_S13,
+    UNW_ARM_S14,
+    UNW_ARM_S15,
+    UNW_ARM_S16,
+    UNW_ARM_S17,
+    UNW_ARM_S18,
+    UNW_ARM_S19,
+    UNW_ARM_S20,
+    UNW_ARM_S21,
+    UNW_ARM_S22,
+    UNW_ARM_S23,
+    UNW_ARM_S24,
+    UNW_ARM_S25,
+    UNW_ARM_S26,
+    UNW_ARM_S27,
+    UNW_ARM_S28,
+    UNW_ARM_S29,
+    UNW_ARM_S30,
+    UNW_ARM_S31,
+    
+    /* FPA register numberings.  */
+    UNW_ARM_F0 = 96,
+    UNW_ARM_F1,
+    UNW_ARM_F2,
+    UNW_ARM_F3,
+    UNW_ARM_F4,
+    UNW_ARM_F5,
+    UNW_ARM_F6,
+    UNW_ARM_F7,
+    
+    /* iWMMXt GR register numberings.  */
+    UNW_ARM_wCGR0 = 104,
+    UNW_ARM_wCGR1,
+    UNW_ARM_wCGR2,
+    UNW_ARM_wCGR3,
+    UNW_ARM_wCGR4,
+    UNW_ARM_wCGR5,
+    UNW_ARM_wCGR6,
+    UNW_ARM_wCGR7,
+    
+    /* iWMMXt register numberings.  */
+    UNW_ARM_wR0 = 112,
+    UNW_ARM_wR1,
+    UNW_ARM_wR2,
+    UNW_ARM_wR3,
+    UNW_ARM_wR4,
+    UNW_ARM_wR5,
+    UNW_ARM_wR6,
+    UNW_ARM_wR7,
+    UNW_ARM_wR8,
+    UNW_ARM_wR9,
+    UNW_ARM_wR10,
+    UNW_ARM_wR11,
+    UNW_ARM_wR12,
+    UNW_ARM_wR13,
+    UNW_ARM_wR14,
+    UNW_ARM_wR15,
+    
+    /* Two-byte encodings from here on.  */
+    
+    /* SPSR.  */
+    UNW_ARM_SPSR = 128,
+    UNW_ARM_SPSR_FIQ,
+    UNW_ARM_SPSR_IRQ,
+    UNW_ARM_SPSR_ABT,
+    UNW_ARM_SPSR_UND,
+    UNW_ARM_SPSR_SVC,
+    
+    /* User mode registers.  */
+    UNW_ARM_R8_USR = 144,
+    UNW_ARM_R9_USR,
+    UNW_ARM_R10_USR,
+    UNW_ARM_R11_USR,
+    UNW_ARM_R12_USR,
+    UNW_ARM_R13_USR,
+    UNW_ARM_R14_USR,
+    
+    /* FIQ registers.  */
+    UNW_ARM_R8_FIQ = 151,
+    UNW_ARM_R9_FIQ,
+    UNW_ARM_R10_FIQ,
+    UNW_ARM_R11_FIQ,
+    UNW_ARM_R12_FIQ,
+    UNW_ARM_R13_FIQ,
+    UNW_ARM_R14_FIQ,
+    
+    /* IRQ registers.  */
+    UNW_ARM_R13_IRQ = 158,
+    UNW_ARM_R14_IRQ,
+    
+    /* ABT registers.  */
+    UNW_ARM_R13_ABT = 160,
+    UNW_ARM_R14_ABT,
+    
+    /* UND registers.  */
+    UNW_ARM_R13_UND = 162,
+    UNW_ARM_R14_UND,
+    
+    /* SVC registers.  */
+    UNW_ARM_R13_SVC = 164,
+    UNW_ARM_R14_SVC,
+    
+    /* iWMMXt control registers.  */
+    UNW_ARM_wC0 = 192,
+    UNW_ARM_wC1,
+    UNW_ARM_wC2,
+    UNW_ARM_wC3,
+    UNW_ARM_wC4,
+    UNW_ARM_wC5,
+    UNW_ARM_wC6,
+    UNW_ARM_wC7,
+
+    /* VFPv3/Neon 64-bit registers.  */
+    UNW_ARM_D0 = 256,
+    UNW_ARM_D1,
+    UNW_ARM_D2,
+    UNW_ARM_D3,
+    UNW_ARM_D4,
+    UNW_ARM_D5,
+    UNW_ARM_D6,
+    UNW_ARM_D7,
+    UNW_ARM_D8,
+    UNW_ARM_D9,
+    UNW_ARM_D10,
+    UNW_ARM_D11,
+    UNW_ARM_D12,
+    UNW_ARM_D13,
+    UNW_ARM_D14,
+    UNW_ARM_D15,
+    UNW_ARM_D16,
+    UNW_ARM_D17,
+    UNW_ARM_D18,
+    UNW_ARM_D19,
+    UNW_ARM_D20,
+    UNW_ARM_D21,
+    UNW_ARM_D22,
+    UNW_ARM_D23,
+    UNW_ARM_D24,
+    UNW_ARM_D25,
+    UNW_ARM_D26,
+    UNW_ARM_D27,
+    UNW_ARM_D28,
+    UNW_ARM_D29,
+    UNW_ARM_D30,
+    UNW_ARM_D31,
+
+    /* For ARM, the CFA is the value of SP (r13) at the call site in the
+       previous frame.  */
+    UNW_ARM_CFA,
+
+    UNW_TDEP_LAST_REG = UNW_ARM_D31,
+
+    UNW_TDEP_IP = UNW_ARM_R14,  /* A little white lie.  */
+    UNW_TDEP_SP = UNW_ARM_R13,
+    UNW_TDEP_EH = UNW_ARM_R0   /* FIXME.  */
+  }
+arm_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   2       /* FIXME for ARM.  */
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On ARM, we define our own unw_tdep_context instead of using ucontext_t.
+   This allows us to support systems that don't support getcontext and
+   therefore do not define ucontext_t.  */
+typedef struct unw_tdep_context
+  {
+    unsigned long regs[16];
+  }
+unw_tdep_context_t;
+
+/* There is no getcontext() on ARM.  Use a stub version which only saves GP
+   registers.  FIXME: Not ideal, may not be sufficient for all libunwind
+   use cases.  Stores pc+8, which is only approximately correct, really.  */
+#ifndef __thumb__
+#define unw_tdep_getcontext(uc) (({                                    \
+  unw_tdep_context_t *unw_ctx = (uc);                                  \
+  register unsigned long *unw_base asm ("r0") = unw_ctx->regs;         \
+  __asm__ __volatile__ (                                               \
+    "stmia %[base], {r0-r15}"                                          \
+    : : [base] "r" (unw_base) : "memory");                             \
+  }), 0)
+#else /* __thumb__ */
+#define unw_tdep_getcontext(uc) (({                                    \
+  unw_tdep_context_t *unw_ctx = (uc);                                  \
+  register unsigned long *unw_base asm ("r0") = unw_ctx->regs;         \
+  __asm__ __volatile__ (                                               \
+    ".align 2\nbx pc\nnop\n.code 32\n"                                 \
+    "stmia %[base], {r0-r15}\n"                                                \
+    "orr %[base], pc, #1\nbx %[base]"                                  \
+    : [base] "+r" (unw_base) : : "memory", "cc");                      \
+  }), 0)
+#endif
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no arm-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-common.h b/external/android-libunwind/include/libunwind-common.h
new file mode 100644 (file)
index 0000000..f4cbc88
--- /dev/null
@@ -0,0 +1,308 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2001-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+/* ANDROID support update. */
+#include <sys/types.h>
+/* End of ANDROID update. */
+
+#define UNW_VERSION_MAJOR      1
+#define UNW_VERSION_MINOR      1
+#define UNW_VERSION_EXTRA      
+
+#define UNW_VERSION_CODE(maj,min)      (((maj) << 16) | (min))
+#define UNW_VERSION    UNW_VERSION_CODE(UNW_VERSION_MAJOR, UNW_VERSION_MINOR)
+
+#define UNW_PASTE2(x,y)        x##y
+#define UNW_PASTE(x,y) UNW_PASTE2(x,y)
+#define UNW_OBJ(fn)    UNW_PASTE(UNW_PREFIX, fn)
+#define UNW_ARCH_OBJ(fn) UNW_PASTE(UNW_PASTE(UNW_PASTE(_U,UNW_TARGET),_), fn)
+
+#ifdef UNW_LOCAL_ONLY
+# ifdef UNW_ADDITIONAL_PREFIX
+#  define UNW_PREFIX   UNW_PASTE(UNW_PASTE(_UUL,UNW_TARGET),_)
+# else
+#  define UNW_PREFIX   UNW_PASTE(UNW_PASTE(_UL,UNW_TARGET),_)
+# endif
+#else /* !UNW_LOCAL_ONLY */
+# ifdef UNW_ADDITIONAL_PREFIX
+#  define UNW_PREFIX   UNW_PASTE(UNW_PASTE(_UU,UNW_TARGET),_)
+# else
+#  define UNW_PREFIX   UNW_PASTE(UNW_PASTE(_U,UNW_TARGET),_)
+# endif
+#endif /* !UNW_LOCAL_ONLY */
+
+/* Error codes.  The unwind routines return the *negated* values of
+   these error codes on error and a non-negative value on success.  */
+typedef enum
+  {
+    UNW_ESUCCESS = 0,          /* no error */
+    UNW_EUNSPEC,               /* unspecified (general) error */
+    UNW_ENOMEM,                        /* out of memory */
+    UNW_EBADREG,               /* bad register number */
+    UNW_EREADONLYREG,          /* attempt to write read-only register */
+    UNW_ESTOPUNWIND,           /* stop unwinding */
+    UNW_EINVALIDIP,            /* invalid IP */
+    UNW_EBADFRAME,             /* bad frame */
+    UNW_EINVAL,                        /* unsupported operation or bad value */
+    UNW_EBADVERSION,           /* unwind info has unsupported version */
+    UNW_ENOINFO                        /* no unwind info found */
+  }
+unw_error_t;
+
+/* The following enum defines the indices for a couple of
+   (pseudo-)registers which have the same meaning across all
+   platforms.  (RO) means read-only.  (RW) means read-write.  General
+   registers (aka "integer registers") are expected to start with
+   index 0.  The number of such registers is architecture-dependent.
+   The remaining indices can be used as an architecture sees fit.  The
+   last valid register index is given by UNW_REG_LAST.  */
+typedef enum
+  {
+    UNW_REG_IP = UNW_TDEP_IP,          /* (rw) instruction pointer (pc) */
+    UNW_REG_SP = UNW_TDEP_SP,          /* (ro) stack pointer */
+    UNW_REG_EH = UNW_TDEP_EH,          /* (rw) exception-handling reg base */
+    UNW_REG_LAST = UNW_TDEP_LAST_REG
+  }
+unw_frame_regnum_t;
+
+/* Number of exception-handler argument registers: */
+#define UNW_NUM_EH_REGS                UNW_TDEP_NUM_EH_REGS
+
+typedef enum
+  {
+    UNW_CACHE_NONE,                    /* no caching */
+    UNW_CACHE_GLOBAL,                  /* shared global cache */
+    UNW_CACHE_PER_THREAD               /* per-thread caching */
+  }
+unw_caching_policy_t;
+
+typedef int unw_regnum_t;
+
+/* The unwind cursor starts at the youngest (most deeply nested) frame
+   and is used to track the frame state as the unwinder steps from
+   frame to frame.  It is safe to make (shallow) copies of variables
+   of this type.  */
+typedef struct unw_cursor
+  {
+    unw_word_t opaque[UNW_TDEP_CURSOR_LEN];
+  }
+unw_cursor_t;
+
+/* This type encapsulates the entire (preserved) machine-state.  */
+typedef unw_tdep_context_t unw_context_t;
+
+/* unw_getcontext() fills the unw_context_t pointed to by UC with the
+   machine state as it exists at the call-site.  For implementation
+   reasons, this needs to be a target-dependent macro.  It's easiest
+   to think of unw_getcontext() as being identical to getcontext(). */
+#define unw_getcontext(uc)             unw_tdep_getcontext(uc)
+
+/* Return 1 if register number R is a floating-point register, zero
+   otherwise.
+   This routine is signal-safe.  */
+#define unw_is_fpreg(r)                        unw_tdep_is_fpreg(r)
+
+typedef unw_tdep_fpreg_t unw_fpreg_t;
+
+typedef struct unw_addr_space *unw_addr_space_t;
+
+/* Each target may define it's own set of flags, but bits 0-15 are
+   reserved for general libunwind-use.  */
+#define UNW_PI_FLAG_FIRST_TDEP_BIT     16
+/* The information comes from a .debug_frame section.  */
+#define UNW_PI_FLAG_DEBUG_FRAME        32
+
+typedef struct unw_proc_info
+  {
+    unw_word_t start_ip;       /* first IP covered by this procedure */
+    unw_word_t end_ip;         /* first IP NOT covered by this procedure */
+    unw_word_t lsda;           /* address of lang.-spec. data area (if any) */
+    unw_word_t handler;                /* optional personality routine */
+    unw_word_t gp;             /* global-pointer value for this procedure */
+    unw_word_t flags;          /* misc. flags */
+
+    int format;                        /* unwind-info format (arch-specific) */
+    int unwind_info_size;      /* size of the information (if applicable) */
+    void *unwind_info;         /* unwind-info (arch-specific) */
+    unw_tdep_proc_info_t extra;        /* target-dependent auxiliary proc-info */
+  }
+unw_proc_info_t;
+
+/* These are backend callback routines that provide access to the
+   state of a "remote" process.  This can be used, for example, to
+   unwind another process through the ptrace() interface.  */
+typedef struct unw_accessors
+  {
+    /* Look up the unwind info associated with instruction-pointer IP.
+       On success, the routine fills in the PROC_INFO structure.  */
+    int (*find_proc_info) (unw_addr_space_t, unw_word_t, unw_proc_info_t *,
+                          int, void *);
+
+    /* Release any resources (e.g., memory) that were allocated for
+       the unwind info returned in by a previous call to
+       find_proc_info() with NEED_UNWIND_INFO set to 1.  */
+    void (*put_unwind_info) (unw_addr_space_t, unw_proc_info_t *, void *);
+
+    /* Return the list-head of the dynamically registered unwind
+       info.  */
+    int (*get_dyn_info_list_addr) (unw_addr_space_t, unw_word_t *, void *);
+
+    /* Access aligned word at address ADDR.  The value is returned
+       according to the endianness of the host (e.g., if the host is
+       little-endian and the target is big-endian, access_mem() needs
+       to byte-swap the value before returning it).  */
+    int (*access_mem) (unw_addr_space_t, unw_word_t, unw_word_t *, int,
+                      void *);
+
+    /* Access register number REG at address ADDR.  */
+    int (*access_reg) (unw_addr_space_t, unw_regnum_t, unw_word_t *, int,
+                      void *);
+
+    /* Access register number REG at address ADDR.  */
+    int (*access_fpreg) (unw_addr_space_t, unw_regnum_t,
+                        unw_fpreg_t *, int, void *);
+
+    int (*resume) (unw_addr_space_t, unw_cursor_t *, void *);
+
+    /* Optional call back to obtain the name of a (static) procedure.
+       Dynamically generated procedures are handled automatically by
+       libunwind.  This callback is optional and may be set to
+       NULL.  */
+    int (*get_proc_name) (unw_addr_space_t, unw_word_t, char *, size_t,
+                         unw_word_t *, void *);
+  }
+unw_accessors_t;
+
+typedef enum unw_save_loc_type
+  {
+    UNW_SLT_NONE,      /* register is not saved ("not an l-value") */
+    UNW_SLT_MEMORY,    /* register has been saved in memory */
+    UNW_SLT_REG                /* register has been saved in (another) register */
+  }
+unw_save_loc_type_t;
+
+typedef struct unw_save_loc
+  {
+    unw_save_loc_type_t type;
+    union
+      {
+       unw_word_t addr;        /* valid if type==UNW_SLT_MEMORY */
+       unw_regnum_t regnum;    /* valid if type==UNW_SLT_REG */
+      }
+    u;
+    unw_tdep_save_loc_t extra; /* target-dependent additional information */
+  }
+unw_save_loc_t;
+
+/* ANDROID support update. */
+typedef struct unw_map_cursor
+  {
+    void *map_list;
+    void *cur_map;
+  }
+unw_map_cursor_t;
+
+typedef struct unw_map
+  {
+    unw_word_t start;
+    unw_word_t end;
+    unw_word_t offset;
+    unw_word_t load_base;
+    char *path;
+    int flags;
+  }
+unw_map_t;
+/* End of ANDROID update. */
+
+/* These routines work both for local and remote unwinding.  */
+
+#define unw_local_access_addr_space_init UNW_OBJ(local_access_addr_space_init)
+#define unw_local_addr_space   UNW_OBJ(local_addr_space)
+#define unw_create_addr_space  UNW_OBJ(create_addr_space)
+#define unw_destroy_addr_space UNW_OBJ(destroy_addr_space)
+#define unw_get_accessors      UNW_ARCH_OBJ(get_accessors)
+#define unw_init_local         UNW_OBJ(init_local)
+#define unw_init_remote                UNW_OBJ(init_remote)
+#define unw_step               UNW_OBJ(step)
+#define unw_resume             UNW_OBJ(resume)
+#define unw_get_proc_info      UNW_OBJ(get_proc_info)
+#define unw_get_proc_info_by_ip        UNW_OBJ(get_proc_info_by_ip)
+#define unw_get_reg            UNW_OBJ(get_reg)
+#define unw_set_reg            UNW_OBJ(set_reg)
+#define unw_get_fpreg          UNW_OBJ(get_fpreg)
+#define unw_set_fpreg          UNW_OBJ(set_fpreg)
+#define unw_get_save_loc       UNW_OBJ(get_save_loc)
+#define unw_is_signal_frame    UNW_OBJ(is_signal_frame)
+#define unw_handle_signal_frame        UNW_OBJ(handle_signal_frame)
+#define unw_get_proc_name      UNW_OBJ(get_proc_name)
+#define unw_get_proc_name_by_ip        UNW_OBJ(get_proc_name_by_ip)
+#define unw_set_caching_policy UNW_OBJ(set_caching_policy)
+#define unw_regname            UNW_ARCH_OBJ(regname)
+#define unw_flush_cache                UNW_ARCH_OBJ(flush_cache)
+#define unw_strerror           UNW_ARCH_OBJ(strerror)
+
+extern void unw_local_access_addr_space_init (unw_addr_space_t);
+extern unw_addr_space_t unw_create_addr_space (unw_accessors_t *, int);
+extern void unw_destroy_addr_space (unw_addr_space_t);
+extern unw_accessors_t *unw_get_accessors (unw_addr_space_t);
+extern void unw_flush_cache (unw_addr_space_t, unw_word_t, unw_word_t);
+extern int unw_set_caching_policy (unw_addr_space_t, unw_caching_policy_t);
+extern const char *unw_regname (unw_regnum_t);
+
+extern int unw_init_local (unw_cursor_t *, unw_context_t *);
+extern int unw_init_remote (unw_cursor_t *, unw_addr_space_t, void *);
+extern int unw_step (unw_cursor_t *);
+extern int unw_resume (unw_cursor_t *);
+extern int unw_get_proc_info (unw_cursor_t *, unw_proc_info_t *);
+extern int unw_get_proc_info_by_ip (unw_addr_space_t, unw_word_t,
+                                   unw_proc_info_t *, void *);
+extern int unw_get_reg (unw_cursor_t *, int, unw_word_t *);
+extern int unw_set_reg (unw_cursor_t *, int, unw_word_t);
+extern int unw_get_fpreg (unw_cursor_t *, int, unw_fpreg_t *);
+extern int unw_set_fpreg (unw_cursor_t *, int, unw_fpreg_t);
+extern int unw_get_save_loc (unw_cursor_t *, int, unw_save_loc_t *);
+extern int unw_is_signal_frame (unw_cursor_t *);
+extern int unw_handle_signal_frame (unw_cursor_t *);
+extern int unw_get_proc_name (unw_cursor_t *, char *, size_t, unw_word_t *);
+extern int unw_get_proc_name_by_ip (unw_addr_space_t, unw_word_t, char *,
+                                   size_t, unw_word_t *, void *);
+extern const char *unw_strerror (int);
+extern int unw_backtrace (void **, int);
+
+/* ANDROID support update. */
+extern int unw_map_local_cursor_valid (unw_map_cursor_t *);
+extern void unw_map_local_cursor_get (unw_map_cursor_t *);
+extern int unw_map_local_cursor_get_next (unw_map_cursor_t *, unw_map_t *);
+extern int unw_map_local_create (void);
+extern void unw_map_local_destroy (void);
+extern void unw_map_set (unw_addr_space_t, unw_map_cursor_t *);
+extern void unw_map_cursor_reset (unw_map_cursor_t *);
+extern void unw_map_cursor_clear (unw_map_cursor_t *);
+extern int unw_map_cursor_create (unw_map_cursor_t *, pid_t);
+extern void unw_map_cursor_destroy (unw_map_cursor_t *);
+extern int unw_map_cursor_get_next (unw_map_cursor_t *, unw_map_t *);
+/* End of ANDROID update. */
+
+extern unw_addr_space_t unw_local_addr_space;
diff --git a/external/android-libunwind/include/libunwind-coredump.h b/external/android-libunwind/include/libunwind-coredump.h
new file mode 100644 (file)
index 0000000..d2b05e7
--- /dev/null
@@ -0,0 +1,73 @@
+/* libunwind - a platform-independent unwind library
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef libunwind_coredump_h
+#define libunwind_coredump_h
+
+#include <libunwind.h>
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+/* Helper routines which make it easy to use libunwind on a coredump.
+   They're available only if UNW_REMOTE_ONLY is _not_ defined and they
+   aren't really part of the libunwind API.  They are implemented in a
+   archive library called libunwind-coredump.a.  */
+
+struct UCD_info;
+
+extern struct UCD_info *_UCD_create(const char *filename);
+extern void _UCD_destroy(struct UCD_info *);
+
+extern int _UCD_get_num_threads(struct UCD_info *);
+extern void _UCD_select_thread(struct UCD_info *, int);
+extern pid_t _UCD_get_pid(struct UCD_info *);
+extern int _UCD_get_cursig(struct UCD_info *);
+extern int _UCD_add_backing_file_at_segment(struct UCD_info *, int phdr_no, const char *filename);
+extern int _UCD_add_backing_file_at_vaddr(struct UCD_info *,
+                                         unsigned long vaddr,
+                                         const char *filename);
+
+extern int _UCD_find_proc_info (unw_addr_space_t, unw_word_t,
+                               unw_proc_info_t *, int, void *);
+extern void _UCD_put_unwind_info (unw_addr_space_t, unw_proc_info_t *, void *);
+extern int _UCD_get_dyn_info_list_addr (unw_addr_space_t, unw_word_t *,
+                                       void *);
+extern int _UCD_access_mem (unw_addr_space_t, unw_word_t, unw_word_t *, int,
+                           void *);
+extern int _UCD_access_reg (unw_addr_space_t, unw_regnum_t, unw_word_t *,
+                           int, void *);
+extern int _UCD_access_fpreg (unw_addr_space_t, unw_regnum_t, unw_fpreg_t *,
+                             int, void *);
+extern int _UCD_get_proc_name (unw_addr_space_t, unw_word_t, char *, size_t,
+                              unw_word_t *, void *);
+extern int _UCD_resume (unw_addr_space_t, unw_cursor_t *, void *);
+extern unw_accessors_t _UCD_accessors;
+
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* libunwind_coredump_h */
diff --git a/external/android-libunwind/include/libunwind-dynamic.h b/external/android-libunwind/include/libunwind-dynamic.h
new file mode 100644 (file)
index 0000000..584f392
--- /dev/null
@@ -0,0 +1,210 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2002-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+/* This file defines the runtime-support routines for dynamically
+generated code.  Even though it is implemented as part of libunwind,
+it is logically separate from the interface to perform the actual
+unwinding.  In particular, this interface is always used in the
+context of the unwind target, whereas the rest of the unwind API is
+used in context of the process that is doing the unwind (which may be
+a debugger running on another machine, for example).
+
+Note that the data-structures declared here server a dual purpose:
+when a program registers a dynamically generated procedure, it uses
+these structures directly.  On the other hand, with remote-unwinding,
+the data-structures are read from the remote process's memory and
+translated into internalized versions.  To facilitate remote-access,
+the following rules should be followed in declaring these structures:
+
+ (1) Declare a member as a pointer only if the the information the
+     member points to needs to be internalized as well (e.g., a
+     string representing a procedure name should be declared as
+     "const char *", but the instruction pointer should be declared
+     as unw_word_t).
+
+ (2) Provide sufficient padding to ensure that no implicit padding
+     will be needed on any of the supported target architectures.  For
+     the time being, padding data structures with the assumption that
+     sizeof (unw_word_t) == 8 should be sufficient.  (Note: it's not
+     impossible to internalize structures with internal padding, but
+     it does make the process a bit harder).
+
+ (3) Don't declare members that contain bitfields or floating-point
+     values.
+
+ (4) Don't declare members with enumeration types.  Declare them as
+     int32_t instead.  */
+
+typedef enum
+  {
+    UNW_DYN_STOP = 0,          /* end-of-unwind-info marker */
+    UNW_DYN_SAVE_REG,          /* save register to another register */
+    UNW_DYN_SPILL_FP_REL,      /* frame-pointer-relative register spill */
+    UNW_DYN_SPILL_SP_REL,      /* stack-pointer-relative register spill */
+    UNW_DYN_ADD,               /* add constant value to a register */
+    UNW_DYN_POP_FRAMES,                /* drop one or more stack frames */
+    UNW_DYN_LABEL_STATE,       /* name the current state */
+    UNW_DYN_COPY_STATE,                /* set the region's entry-state */
+    UNW_DYN_ALIAS              /* get unwind info from an alias */
+  }
+unw_dyn_operation_t;
+
+typedef enum
+  {
+    UNW_INFO_FORMAT_DYNAMIC,           /* unw_dyn_proc_info_t */
+    UNW_INFO_FORMAT_TABLE,             /* unw_dyn_table_t */
+    UNW_INFO_FORMAT_REMOTE_TABLE,      /* unw_dyn_remote_table_t */
+    UNW_INFO_FORMAT_ARM_EXIDX          /* ARM specific unwind info */
+  }
+unw_dyn_info_format_t;
+
+typedef struct unw_dyn_op
+  {
+    int8_t tag;                                /* what operation? */
+    int8_t qp;                         /* qualifying predicate register */
+    int16_t reg;                       /* what register */
+    int32_t when;                      /* when does it take effect? */
+    unw_word_t val;                    /* auxiliary value */
+  }
+unw_dyn_op_t;
+
+typedef struct unw_dyn_region_info
+  {
+    struct unw_dyn_region_info *next;  /* linked list of regions */
+    int32_t insn_count;                        /* region length (# of instructions) */
+    uint32_t op_count;                 /* length of op-array */
+    unw_dyn_op_t op[1];                        /* variable-length op-array */
+  }
+unw_dyn_region_info_t;
+
+typedef struct unw_dyn_proc_info
+  {
+    unw_word_t name_ptr;       /* address of human-readable procedure name */
+    unw_word_t handler;                /* address of personality routine */
+    uint32_t flags;
+    int32_t pad0;
+    unw_dyn_region_info_t *regions;
+  }
+unw_dyn_proc_info_t;
+
+typedef struct unw_dyn_table_info
+  {
+    unw_word_t name_ptr;       /* addr. of table name (e.g., library name) */
+    unw_word_t segbase;                /* segment base */
+    unw_word_t table_len;      /* must be a multiple of sizeof(unw_word_t)! */
+    unw_word_t *table_data;
+  }
+unw_dyn_table_info_t;
+
+typedef struct unw_dyn_remote_table_info
+  {
+    unw_word_t name_ptr;       /* addr. of table name (e.g., library name) */
+    unw_word_t segbase;                /* segment base */
+    unw_word_t table_len;      /* must be a multiple of sizeof(unw_word_t)! */
+    unw_word_t table_data;
+  }
+unw_dyn_remote_table_info_t;
+
+typedef struct unw_dyn_info
+  {
+    /* doubly-linked list of dyn-info structures: */
+    struct unw_dyn_info *next;
+    struct unw_dyn_info *prev;
+    unw_word_t start_ip;       /* first IP covered by this entry */
+    unw_word_t end_ip;         /* first IP NOT covered by this entry */
+    unw_word_t gp;             /* global-pointer in effect for this entry */
+    int32_t format;            /* real type: unw_dyn_info_format_t */
+    int32_t pad;
+    union
+      {
+       unw_dyn_proc_info_t pi;
+       unw_dyn_table_info_t ti;
+       unw_dyn_remote_table_info_t rti;
+      }
+    u;
+  }
+unw_dyn_info_t;
+
+typedef struct unw_dyn_info_list
+  {
+    uint32_t version;
+    uint32_t generation;
+    unw_dyn_info_t *first;
+  }
+unw_dyn_info_list_t;
+
+/* Return the size (in bytes) of an unw_dyn_region_info_t structure that can
+   hold OP_COUNT ops.  */
+#define _U_dyn_region_info_size(op_count)                              \
+       ((char *) (((unw_dyn_region_info_t *) NULL)->op + (op_count))   \
+        - (char *) NULL)
+
+/* Register the unwind info for a single procedure.
+   This routine is NOT signal-safe.  */
+extern void _U_dyn_register (unw_dyn_info_t *);
+
+/* Cancel the unwind info for a single procedure.
+   This routine is NOT signal-safe.  */
+extern void _U_dyn_cancel (unw_dyn_info_t *);
+
+\f
+/* Convenience routines.  */
+
+#define _U_dyn_op(_tag, _qp, _when, _reg, _val)                                \
+       ((unw_dyn_op_t) { (_tag), (_qp), (_reg), (_when), (_val) })
+
+#define _U_dyn_op_save_reg(op, qp, when, reg, dst)                     \
+       (*(op) = _U_dyn_op (UNW_DYN_SAVE_REG, (qp), (when), (reg), (dst)))
+
+#define _U_dyn_op_spill_fp_rel(op, qp, when, reg, offset)              \
+       (*(op) = _U_dyn_op (UNW_DYN_SPILL_FP_REL, (qp), (when), (reg),  \
+                           (offset)))
+
+#define _U_dyn_op_spill_sp_rel(op, qp, when, reg, offset)              \
+       (*(op) = _U_dyn_op (UNW_DYN_SPILL_SP_REL, (qp), (when), (reg),  \
+                           (offset)))
+
+#define _U_dyn_op_add(op, qp, when, reg, value)                                \
+       (*(op) = _U_dyn_op (UNW_DYN_ADD, (qp), (when), (reg), (value)))
+
+#define _U_dyn_op_pop_frames(op, qp, when, num_frames)                 \
+       (*(op) = _U_dyn_op (UNW_DYN_POP_FRAMES, (qp), (when), 0, (num_frames)))
+
+#define _U_dyn_op_label_state(op, label)                               \
+       (*(op) = _U_dyn_op (UNW_DYN_LABEL_STATE, _U_QP_TRUE, -1, 0, (label)))
+
+#define _U_dyn_op_copy_state(op, label)                                        \
+       (*(op) = _U_dyn_op (UNW_DYN_COPY_STATE, _U_QP_TRUE, -1, 0, (label)))
+
+#define _U_dyn_op_alias(op, qp, when, addr)                            \
+       (*(op) = _U_dyn_op (UNW_DYN_ALIAS, (qp), (when), 0, (addr)))
+
+#define _U_dyn_op_stop(op)                                             \
+       (*(op) = _U_dyn_op (UNW_DYN_STOP, _U_QP_TRUE, -1, 0, 0))
+
+/* The target-dependent qualifying predicate which is always TRUE.  On
+   IA-64, that's p0 (0), on non-predicated architectures, the value is
+   ignored.  */
+#define _U_QP_TRUE     _U_TDEP_QP_TRUE
diff --git a/external/android-libunwind/include/libunwind-hppa.h b/external/android-libunwind/include/libunwind-hppa.h
new file mode 100644 (file)
index 0000000..b5fba56
--- /dev/null
@@ -0,0 +1,131 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2003-2004 Hewlett-Packard Co
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <ucontext.h>
+
+#define UNW_TARGET     hppa
+#define UNW_TARGET_HPPA        1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+#define UNW_TDEP_CURSOR_LEN    511
+
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+
+typedef union
+  {
+    struct { unw_word_t bits[2]; } raw;
+    double val;
+  }
+unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    /* Note: general registers are expected to start with index 0.
+       This convention facilitates architecture-independent
+       implementation of the C++ exception handling ABI.  See
+       _Unwind_SetGR() and _Unwind_GetGR() for details.  */
+    UNW_HPPA_GR = 0,
+     UNW_HPPA_RP = 2,                  /* return pointer */
+     UNW_HPPA_FP = 3,                  /* frame pointer */
+     UNW_HPPA_SP = UNW_HPPA_GR + 30,
+
+    UNW_HPPA_FR = UNW_HPPA_GR + 32,
+
+    UNW_HPPA_IP = UNW_HPPA_FR + 32,    /* instruction pointer */
+
+    /* other "preserved" registers (fpsr etc.)... */
+
+    /* PA-RISC has 4 exception-argument registers but they're not
+       contiguous.  To deal with this, we define 4 pseudo
+       exception-handling registers which we then alias to the actual
+       physical register.  */
+
+    UNW_HPPA_EH0 = UNW_HPPA_IP + 1,    /* alias for UNW_HPPA_GR + 20 */
+    UNW_HPPA_EH1 = UNW_HPPA_EH0 + 1,   /* alias for UNW_HPPA_GR + 21 */
+    UNW_HPPA_EH2 = UNW_HPPA_EH1 + 1,   /* alias for UNW_HPPA_GR + 22 */
+    UNW_HPPA_EH3 = UNW_HPPA_EH2 + 1,   /* alias for UNW_HPPA_GR + 31 */
+
+    /* frame info (read-only) */
+    UNW_HPPA_CFA,
+
+    UNW_TDEP_LAST_REG = UNW_HPPA_IP,
+
+    UNW_TDEP_IP = UNW_HPPA_IP,
+    UNW_TDEP_SP = UNW_HPPA_SP,
+    UNW_TDEP_EH = UNW_HPPA_EH0
+  }
+hppa_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   4
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On PA-RISC, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+#define unw_tdep_is_fpreg(r)           ((unsigned) ((r) - UNW_HPPA_FR) < 32)
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no PA-RISC-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_getcontext            UNW_ARCH_OBJ (getcontext)
+extern int unw_tdep_getcontext (unw_tdep_context_t *);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-ia64.h b/external/android-libunwind/include/libunwind-ia64.h
new file mode 100644 (file)
index 0000000..4dcc4f9
--- /dev/null
@@ -0,0 +1,197 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2001-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#include <inttypes.h>
+#include <ucontext.h>
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#ifdef ia64
+  /* This works around a bug in Intel's ECC v7.0 which defines "ia64"
+     as "1".  */
+# undef ia64
+#endif
+
+#ifdef __hpux
+  /* On HP-UX, there is no hope of supporting UNW_LOCAL_ONLY, because
+     it's impossible to obtain the address of the members in the
+     sigcontext structure.  */
+# undef UNW_LOCAL_ONLY
+# define UNW_GENERIC_ONLY
+#endif
+
+#define UNW_TARGET     ia64
+#define UNW_TARGET_IA64        1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+#define UNW_TDEP_CURSOR_LEN    511
+
+/* If this bit is it indicates that the procedure saved all of ar.bsp,
+   ar.bspstore, and ar.rnat.  If, additionally, ar.bsp != saved ar.bsp,
+   then this procedure has performed a register-backing-store switch.  */
+#define UNW_PI_FLAG_IA64_RBS_SWITCH_BIT        (UNW_PI_FLAG_FIRST_TDEP_BIT + 0)
+
+#define UNW_PI_FLAG_IA64_RBS_SWITCH    (1 << UNW_PI_FLAG_IA64_RBS_SWITCH_BIT)
+
+typedef uint64_t unw_word_t;
+typedef int64_t unw_sword_t;
+
+/* On IA-64, we want to access the contents of floating-point
+   registers as a pair of "words", but to ensure 16-byte alignment, we
+   make it a union that contains a "long double".  This will do the
+   Right Thing on all known IA-64 platforms, including HP-UX.  */
+typedef union
+  {
+    struct { unw_word_t bits[2]; } raw;
+    long double dummy; /* dummy to force 16-byte alignment */
+  }
+unw_tdep_fpreg_t;
+
+typedef struct
+  {
+    /* no ia64-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+typedef enum
+  {
+    /* Note: general registers are excepted to start with index 0.
+       This convention facilitates architecture-independent
+       implementation of the C++ exception handling ABI.  See
+       _Unwind_SetGR() and _Unwind_GetGR() for details.  */
+    UNW_IA64_GR = 0,                   /* general registers (r0..r127) */
+     UNW_IA64_GP = UNW_IA64_GR + 1,
+     UNW_IA64_TP = UNW_IA64_GR + 13,
+
+    UNW_IA64_NAT = UNW_IA64_GR + 128,  /* NaT registers (nat0..nat127) */
+
+    UNW_IA64_FR = UNW_IA64_NAT + 128,  /* fp registers (f0..f127) */
+
+    UNW_IA64_AR = UNW_IA64_FR + 128,   /* application registers (ar0..r127) */
+     UNW_IA64_AR_RSC = UNW_IA64_AR + 16,
+     UNW_IA64_AR_BSP = UNW_IA64_AR + 17,
+     UNW_IA64_AR_BSPSTORE = UNW_IA64_AR + 18,
+     UNW_IA64_AR_RNAT = UNW_IA64_AR + 19,
+     UNW_IA64_AR_CSD = UNW_IA64_AR + 25,
+     UNW_IA64_AR_26 = UNW_IA64_AR + 26,
+     UNW_IA64_AR_SSD = UNW_IA64_AR_26,
+     UNW_IA64_AR_CCV = UNW_IA64_AR + 32,
+     UNW_IA64_AR_UNAT = UNW_IA64_AR + 36,
+     UNW_IA64_AR_FPSR = UNW_IA64_AR + 40,
+     UNW_IA64_AR_PFS = UNW_IA64_AR + 64,
+     UNW_IA64_AR_LC = UNW_IA64_AR + 65,
+     UNW_IA64_AR_EC = UNW_IA64_AR + 66,
+
+    UNW_IA64_BR = UNW_IA64_AR + 128,   /* branch registers (b0..p7) */
+      UNW_IA64_RP = UNW_IA64_BR + 0,   /* return pointer (rp) */
+    UNW_IA64_PR = UNW_IA64_BR + 8,     /* predicate registers (p0..p63) */
+    UNW_IA64_CFM,
+
+    /* frame info: */
+    UNW_IA64_BSP,
+    UNW_IA64_IP,
+    UNW_IA64_SP,
+
+    UNW_TDEP_LAST_REG = UNW_IA64_SP,
+
+    UNW_TDEP_IP = UNW_IA64_IP,
+    UNW_TDEP_SP = UNW_IA64_SP,
+    UNW_TDEP_EH = UNW_IA64_GR + 15
+  }
+ia64_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   4       /* r15-r18 are exception args */
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  On IA-64,
+       we use this to provide the bit number in which a NaT bit gets
+       saved.  */
+    uint8_t nat_bitnr;
+
+    /* Padding reserved for future use.  */
+    uint8_t reserved[7];
+  }
+unw_tdep_save_loc_t;
+
+/* On IA-64, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+#define unw_tdep_is_fpreg(r)           ((unsigned) ((r) - UNW_IA64_FR) < 128)
+
+#include "libunwind-dynamic.h"
+#include "libunwind-common.h"
+
+#ifdef __hpux
+  /* In theory, we could use _Uia64_getcontext() on HP-UX as well, but
+     the benefit of doing so would be marginal given that it can't
+     support UNW_LOCAL_ONLY.  */
+# define unw_tdep_getcontext           getcontext
+#else
+# define unw_tdep_getcontext           UNW_ARCH_OBJ (getcontext)
+  extern int unw_tdep_getcontext (unw_tdep_context_t *);
+#endif
+
+/* This is a helper routine to search an ia64 unwind table.  If the
+   address-space argument AS points to something other than the local
+   address-space, the memory for the unwind-info will be allocated
+   with malloc(), and should be free()d during the put_unwind_info()
+   callback.  This routine is signal-safe for the local-address-space
+   case ONLY.  */
+#define unw_search_ia64_unwind_table   UNW_OBJ(search_unwind_table)
+extern int unw_search_ia64_unwind_table (unw_addr_space_t, unw_word_t,
+                                        unw_dyn_info_t *, unw_proc_info_t *,
+                                        int, void *);
+
+/* This is a helper routine which the get_dyn_info_list_addr()
+   callback can use to locate the special dynamic-info list entry in
+   an IA-64 unwind table.  If the entry exists in the table, the
+   list-address is returned.  In all other cases, 0 is returned.  */
+extern unw_word_t _Uia64_find_dyn_list (unw_addr_space_t, unw_dyn_info_t *,
+                                       void *);
+
+/* This is a helper routine to obtain the kernel-unwind info.  It is
+   signal-safe.  */
+extern int _Uia64_get_kernel_table (unw_dyn_info_t *);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-mips.h b/external/android-libunwind/include/libunwind-mips.h
new file mode 100644 (file)
index 0000000..83e44de
--- /dev/null
@@ -0,0 +1,163 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2008 CodeSourcery
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <ucontext.h>
+
+#ifdef mips
+# undef mips
+#endif
+
+#define UNW_TARGET     mips
+#define UNW_TARGET_MIPS        1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+   
+/* FIXME for MIPS. Too big?  What do other things use for similar tasks?  */
+#define UNW_TDEP_CURSOR_LEN    4096
+
+/* The size of a "word" varies on MIPS.  This type is used for memory
+   addresses and register values.  To allow a single library to support
+   multiple ABIs, and to support N32 at all, we must use a 64-bit type
+   even when addresses are only 32 bits.  */
+typedef uint64_t unw_word_t;
+typedef int32_t unw_sword_t;
+
+/* FIXME: MIPS ABIs.  */
+typedef long double unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    UNW_MIPS_R0,
+    UNW_MIPS_R1,
+    UNW_MIPS_R2,
+    UNW_MIPS_R3,
+    UNW_MIPS_R4,
+    UNW_MIPS_R5,
+    UNW_MIPS_R6,
+    UNW_MIPS_R7,
+    UNW_MIPS_R8,
+    UNW_MIPS_R9,
+    UNW_MIPS_R10,
+    UNW_MIPS_R11,
+    UNW_MIPS_R12,
+    UNW_MIPS_R13,
+    UNW_MIPS_R14,
+    UNW_MIPS_R15,
+    UNW_MIPS_R16,
+    UNW_MIPS_R17,
+    UNW_MIPS_R18,
+    UNW_MIPS_R19,
+    UNW_MIPS_R20,
+    UNW_MIPS_R21,
+    UNW_MIPS_R22,
+    UNW_MIPS_R23,
+    UNW_MIPS_R24,
+    UNW_MIPS_R25,
+    UNW_MIPS_R26,
+    UNW_MIPS_R27,
+    UNW_MIPS_R28,
+    UNW_MIPS_R29,
+    UNW_MIPS_R30,
+    UNW_MIPS_R31,
+
+    UNW_MIPS_PC = 34,
+
+    /* FIXME: Other registers!  */
+
+    /* For MIPS, the CFA is the value of SP (r29) at the call site in the
+       previous frame.  */
+    UNW_MIPS_CFA,
+
+    UNW_TDEP_LAST_REG = UNW_MIPS_R31,
+
+    UNW_TDEP_IP = UNW_MIPS_R31,
+    UNW_TDEP_SP = UNW_MIPS_R29,
+    UNW_TDEP_EH = UNW_MIPS_R0   /* FIXME.  */
+  }
+mips_regnum_t;
+
+typedef enum
+  {
+    UNW_MIPS_ABI_O32,
+    UNW_MIPS_ABI_N32,
+    UNW_MIPS_ABI_N64
+  }
+mips_abi_t;
+
+#define UNW_TDEP_NUM_EH_REGS   2       /* FIXME for MIPS.  */
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On x86, we can directly use ucontext_t as the unwind context.  FIXME for
+   MIPS.  */
+typedef ucontext_t unw_tdep_context_t;
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no mips-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+/* There is no getcontext() on MIPS.  Use a stub version which only saves GP
+   registers.  FIXME: Not ideal, may not be sufficient for all libunwind
+   use cases.  */
+#define unw_tdep_getcontext UNW_ARCH_OBJ(getcontext)
+extern int unw_tdep_getcontext (ucontext_t *uc);
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-ppc32.h b/external/android-libunwind/include/libunwind-ppc32.h
new file mode 100644 (file)
index 0000000..51852e8
--- /dev/null
@@ -0,0 +1,213 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2006-2007 IBM
+   Contributed by
+     Corey Ashford <cjashfor@us.ibm.com>
+     Jose Flavio Aguilar Paulino <jflavio@br.ibm.com> <joseflavio@gmail.com>
+
+   Copied from libunwind-x86_64.h, modified slightly for building
+   frysk successfully on ppc64, by Wu Zhou <woodzltc@cn.ibm.com>
+   Will be replaced when libunwind is ready on ppc64 platform.
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <ucontext.h>
+
+#define UNW_TARGET             ppc32
+#define UNW_TARGET_PPC32       1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/*
+ * This needs to be big enough to accommodate "struct cursor", while
+ * leaving some slack for future expansion.  Changing this value will
+ * require recompiling all users of this library.  Stack allocation is
+ * relatively cheap and unwind-state copying is relatively rare, so we want
+ * to err on making it rather too big than too small.
+ *
+ * To simplify this whole process, we are at least initially taking the
+ * tack that UNW_PPC32_* map straight across to the .eh_frame column register
+ * numbers.  These register numbers come from gcc's source in
+ * gcc/config/rs6000/rs6000.h
+ *
+ * UNW_TDEP_CURSOR_LEN is in terms of unw_word_t size.  Since we have 115
+ * elements in the loc array, each sized 2 * unw_word_t, plus the rest of
+ * the cursor struct, this puts us at about 2 * 115 + 40 = 270.  Let's
+ * round that up to 280.
+ */
+
+#define UNW_TDEP_CURSOR_LEN 280
+
+#if __WORDSIZE==32
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+#else
+typedef uint64_t unw_word_t;
+typedef int64_t unw_sword_t;
+#endif
+
+typedef long double unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    UNW_PPC32_R0,
+    UNW_PPC32_R1, /* called STACK_POINTER in gcc */
+    UNW_PPC32_R2,
+    UNW_PPC32_R3,
+    UNW_PPC32_R4,
+    UNW_PPC32_R5,
+    UNW_PPC32_R6,
+    UNW_PPC32_R7,
+    UNW_PPC32_R8,
+    UNW_PPC32_R9,
+    UNW_PPC32_R10,
+    UNW_PPC32_R11, /* called STATIC_CHAIN in gcc */
+    UNW_PPC32_R12,
+    UNW_PPC32_R13,
+    UNW_PPC32_R14,
+    UNW_PPC32_R15,
+    UNW_PPC32_R16,
+    UNW_PPC32_R17,
+    UNW_PPC32_R18,
+    UNW_PPC32_R19,
+    UNW_PPC32_R20,
+    UNW_PPC32_R21,
+    UNW_PPC32_R22,
+    UNW_PPC32_R23,
+    UNW_PPC32_R24,
+    UNW_PPC32_R25,
+    UNW_PPC32_R26,
+    UNW_PPC32_R27,
+    UNW_PPC32_R28,
+    UNW_PPC32_R29,
+    UNW_PPC32_R30,
+    UNW_PPC32_R31, /* called HARD_FRAME_POINTER in gcc */
+
+    /* Count Register */
+    UNW_PPC32_CTR = 32,
+    /* Fixed-Point Status and Control Register */
+    UNW_PPC32_XER = 33,
+    /* Condition Register */
+    UNW_PPC32_CCR = 34,
+    /* Machine State Register */
+    //UNW_PPC32_MSR = 35,
+    /* MQ or SPR0, not part of generic Power, part of MPC601 */
+    //UNW_PPC32_MQ = 36,
+    /* Link Register */
+    UNW_PPC32_LR = 36,
+    /* Floating Pointer Status and Control Register */
+    UNW_PPC32_FPSCR = 37,
+
+    UNW_PPC32_F0 = 48,
+    UNW_PPC32_F1,
+    UNW_PPC32_F2,
+    UNW_PPC32_F3,
+    UNW_PPC32_F4,
+    UNW_PPC32_F5,
+    UNW_PPC32_F6,
+    UNW_PPC32_F7,
+    UNW_PPC32_F8,
+    UNW_PPC32_F9,
+    UNW_PPC32_F10,
+    UNW_PPC32_F11,
+    UNW_PPC32_F12,
+    UNW_PPC32_F13,
+    UNW_PPC32_F14,
+    UNW_PPC32_F15,
+    UNW_PPC32_F16,
+    UNW_PPC32_F17,
+    UNW_PPC32_F18,
+    UNW_PPC32_F19,
+    UNW_PPC32_F20,
+    UNW_PPC32_F21,
+    UNW_PPC32_F22,
+    UNW_PPC32_F23,
+    UNW_PPC32_F24,
+    UNW_PPC32_F25,
+    UNW_PPC32_F26,
+    UNW_PPC32_F27,
+    UNW_PPC32_F28,
+    UNW_PPC32_F29,
+    UNW_PPC32_F30,
+    UNW_PPC32_F31,
+
+    UNW_TDEP_LAST_REG = UNW_PPC32_F31,
+
+    UNW_TDEP_IP = UNW_PPC32_LR,
+    UNW_TDEP_SP = UNW_PPC32_R1,
+    UNW_TDEP_EH = UNW_PPC32_R12
+  }
+ppc32_regnum_t;
+
+/*
+ * According to David Edelsohn, GNU gcc uses R3, R4, R5, and maybe R6 for
+ * passing parameters to exception handlers.
+ */
+
+#define UNW_TDEP_NUM_EH_REGS   4
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On ppc, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+/* XXX this is not ideal: an application should not be prevented from
+   using the "getcontext" name just because it's using libunwind.  We
+   can't just use __getcontext() either, because that isn't exported
+   by glibc...  */
+#define unw_tdep_getcontext(uc)                (getcontext (uc), 0)
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no ppc32-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-ppc64.h b/external/android-libunwind/include/libunwind-ppc64.h
new file mode 100644 (file)
index 0000000..e0dbaaa
--- /dev/null
@@ -0,0 +1,270 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2006-2007 IBM
+   Contributed by
+     Corey Ashford <cjashfor@us.ibm.com>
+     Jose Flavio Aguilar Paulino <jflavio@br.ibm.com> <joseflavio@gmail.com>
+
+   Copied from libunwind-x86_64.h, modified slightly for building
+   frysk successfully on ppc64, by Wu Zhou <woodzltc@cn.ibm.com>
+   Will be replaced when libunwind is ready on ppc64 platform.
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <ucontext.h>
+
+#define UNW_TARGET             ppc64
+#define UNW_TARGET_PPC64       1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/*
+ * This needs to be big enough to accommodate "struct cursor", while
+ * leaving some slack for future expansion.  Changing this value will
+ * require recompiling all users of this library.  Stack allocation is
+ * relatively cheap and unwind-state copying is relatively rare, so we want
+ * to err on making it rather too big than too small.
+ *
+ * To simplify this whole process, we are at least initially taking the
+ * tack that UNW_PPC64_* map straight across to the .eh_frame column register
+ * numbers.  These register numbers come from gcc's source in
+ * gcc/config/rs6000/rs6000.h
+ *
+ * UNW_TDEP_CURSOR_LEN is in terms of unw_word_t size.  Since we have 115
+ * elements in the loc array, each sized 2 * unw_word_t, plus the rest of
+ * the cursor struct, this puts us at about 2 * 115 + 40 = 270.  Let's
+ * round that up to 280.
+ */
+
+#define UNW_TDEP_CURSOR_LEN 280
+
+#if __WORDSIZE==32
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+#else
+typedef uint64_t unw_word_t;
+typedef int64_t unw_sword_t;
+#endif
+
+typedef long double unw_tdep_fpreg_t;
+
+/*
+ * Vector register (in PowerPC64 used for AltiVec registers)
+ */
+typedef struct {
+    uint64_t halves[2];
+} unw_tdep_vreg_t;
+
+typedef enum
+  {
+    UNW_PPC64_R0,
+    UNW_PPC64_R1, /* called STACK_POINTER in gcc */
+    UNW_PPC64_R2,
+    UNW_PPC64_R3,
+    UNW_PPC64_R4,
+    UNW_PPC64_R5,
+    UNW_PPC64_R6,
+    UNW_PPC64_R7,
+    UNW_PPC64_R8,
+    UNW_PPC64_R9,
+    UNW_PPC64_R10,
+    UNW_PPC64_R11, /* called STATIC_CHAIN in gcc */
+    UNW_PPC64_R12,
+    UNW_PPC64_R13,
+    UNW_PPC64_R14,
+    UNW_PPC64_R15,
+    UNW_PPC64_R16,
+    UNW_PPC64_R17,
+    UNW_PPC64_R18,
+    UNW_PPC64_R19,
+    UNW_PPC64_R20,
+    UNW_PPC64_R21,
+    UNW_PPC64_R22,
+    UNW_PPC64_R23,
+    UNW_PPC64_R24,
+    UNW_PPC64_R25,
+    UNW_PPC64_R26,
+    UNW_PPC64_R27,
+    UNW_PPC64_R28,
+    UNW_PPC64_R29,
+    UNW_PPC64_R30,
+    UNW_PPC64_R31, /* called HARD_FRAME_POINTER in gcc */
+
+    UNW_PPC64_F0 = 32,
+    UNW_PPC64_F1,
+    UNW_PPC64_F2,
+    UNW_PPC64_F3,
+    UNW_PPC64_F4,
+    UNW_PPC64_F5,
+    UNW_PPC64_F6,
+    UNW_PPC64_F7,
+    UNW_PPC64_F8,
+    UNW_PPC64_F9,
+    UNW_PPC64_F10,
+    UNW_PPC64_F11,
+    UNW_PPC64_F12,
+    UNW_PPC64_F13,
+    UNW_PPC64_F14,
+    UNW_PPC64_F15,
+    UNW_PPC64_F16,
+    UNW_PPC64_F17,
+    UNW_PPC64_F18,
+    UNW_PPC64_F19,
+    UNW_PPC64_F20,
+    UNW_PPC64_F21,
+    UNW_PPC64_F22,
+    UNW_PPC64_F23,
+    UNW_PPC64_F24,
+    UNW_PPC64_F25,
+    UNW_PPC64_F26,
+    UNW_PPC64_F27,
+    UNW_PPC64_F28,
+    UNW_PPC64_F29,
+    UNW_PPC64_F30,
+    UNW_PPC64_F31,
+    /* Note that there doesn't appear to be an .eh_frame register column
+       for the FPSCR register.  I don't know why this is.  Since .eh_frame
+       info is what this implementation uses for unwinding, we have no way
+       to unwind this register, and so we will not expose an FPSCR register
+       number in the libunwind API.
+     */
+
+    UNW_PPC64_LR = 65,
+    UNW_PPC64_CTR = 66,
+    UNW_PPC64_ARG_POINTER = 67,
+
+    UNW_PPC64_CR0 = 68,
+    UNW_PPC64_CR1,
+    UNW_PPC64_CR2,
+    UNW_PPC64_CR3,
+    UNW_PPC64_CR4,
+    /* CR5 .. CR7 are currently unused */
+    UNW_PPC64_CR5,
+    UNW_PPC64_CR6,
+    UNW_PPC64_CR7,
+
+    UNW_PPC64_XER = 76,
+
+    UNW_PPC64_V0 = 77,
+    UNW_PPC64_V1,
+    UNW_PPC64_V2,
+    UNW_PPC64_V3,
+    UNW_PPC64_V4,
+    UNW_PPC64_V5,
+    UNW_PPC64_V6,
+    UNW_PPC64_V7,
+    UNW_PPC64_V8,
+    UNW_PPC64_V9,
+    UNW_PPC64_V10,
+    UNW_PPC64_V11,
+    UNW_PPC64_V12,
+    UNW_PPC64_V13,
+    UNW_PPC64_V14,
+    UNW_PPC64_V15,
+    UNW_PPC64_V16,
+    UNW_PPC64_V17,
+    UNW_PPC64_V18,
+    UNW_PPC64_V19,
+    UNW_PPC64_V20,
+    UNW_PPC64_V21,
+    UNW_PPC64_V22,
+    UNW_PPC64_V23,
+    UNW_PPC64_V24,
+    UNW_PPC64_V25,
+    UNW_PPC64_V26,
+    UNW_PPC64_V27,
+    UNW_PPC64_V28,
+    UNW_PPC64_V29,
+    UNW_PPC64_V30,
+    UNW_PPC64_V31,
+
+    UNW_PPC64_VRSAVE = 109,
+    UNW_PPC64_VSCR = 110,
+    UNW_PPC64_SPE_ACC = 111,
+    UNW_PPC64_SPEFSCR = 112,
+
+    /* frame info (read-only) */
+    UNW_PPC64_FRAME_POINTER,
+    UNW_PPC64_NIP,
+
+
+    UNW_TDEP_LAST_REG = UNW_PPC64_NIP,
+
+    UNW_TDEP_IP = UNW_PPC64_NIP,
+    UNW_TDEP_SP = UNW_PPC64_R1,
+    UNW_TDEP_EH = UNW_PPC64_R12
+  }
+ppc64_regnum_t;
+
+/*
+ * According to David Edelsohn, GNU gcc uses R3, R4, R5, and maybe R6 for
+ * passing parameters to exception handlers.
+ */
+
+#define UNW_TDEP_NUM_EH_REGS   4
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On ppc64, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+/* XXX this is not ideal: an application should not be prevented from
+   using the "getcontext" name just because it's using libunwind.  We
+   can't just use __getcontext() either, because that isn't exported
+   by glibc...  */
+#define unw_tdep_getcontext(uc)                (getcontext (uc), 0)
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no ppc64-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-ptrace.h b/external/android-libunwind/include/libunwind-ptrace.h
new file mode 100644 (file)
index 0000000..7fca205
--- /dev/null
@@ -0,0 +1,63 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef libunwind_ptrace_h
+#define libunwind_ptrace_h
+
+#include <libunwind.h>
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+/* Helper routines which make it easy to use libunwind via ptrace().
+   They're available only if UNW_REMOTE_ONLY is _not_ defined and they
+   aren't really part of the libunwind API.  They are implemented in a
+   archive library called libunwind-ptrace.a.  */
+
+extern void *_UPT_create (pid_t);
+extern void _UPT_destroy (void *);
+extern int _UPT_find_proc_info (unw_addr_space_t, unw_word_t,
+                               unw_proc_info_t *, int, void *);
+extern void _UPT_put_unwind_info (unw_addr_space_t, unw_proc_info_t *, void *);
+extern int _UPT_get_dyn_info_list_addr (unw_addr_space_t, unw_word_t *,
+                                       void *);
+extern int _UPT_access_mem (unw_addr_space_t, unw_word_t, unw_word_t *, int,
+                           void *);
+extern int _UPT_access_reg (unw_addr_space_t, unw_regnum_t, unw_word_t *,
+                           int, void *);
+extern int _UPT_access_fpreg (unw_addr_space_t, unw_regnum_t, unw_fpreg_t *,
+                             int, void *);
+extern int _UPT_get_proc_name (unw_addr_space_t, unw_word_t, char *, size_t,
+                              unw_word_t *, void *);
+extern int _UPT_resume (unw_addr_space_t, unw_cursor_t *, void *);
+extern unw_accessors_t _UPT_accessors;
+
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* libunwind_ptrace_h */
diff --git a/external/android-libunwind/include/libunwind-sh.h b/external/android-libunwind/include/libunwind-sh.h
new file mode 100644 (file)
index 0000000..8f36a25
--- /dev/null
@@ -0,0 +1,120 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2008 CodeSourcery
+   Copyright (C) 2012 Tommi Rantala <tt.rantala@gmail.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <stddef.h>
+#include <ucontext.h>
+
+#define UNW_TARGET     sh
+#define UNW_TARGET_SH  1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+
+#define UNW_TDEP_CURSOR_LEN    4096
+
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+
+typedef long double unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    UNW_SH_R0,
+    UNW_SH_R1,
+    UNW_SH_R2,
+    UNW_SH_R3,
+    UNW_SH_R4,
+    UNW_SH_R5,
+    UNW_SH_R6,
+    UNW_SH_R7,
+    UNW_SH_R8,
+    UNW_SH_R9,
+    UNW_SH_R10,
+    UNW_SH_R11,
+    UNW_SH_R12,
+    UNW_SH_R13,
+    UNW_SH_R14,
+    UNW_SH_R15,
+
+    UNW_SH_PC,
+    UNW_SH_PR,
+
+    UNW_TDEP_LAST_REG = UNW_SH_PR,
+
+    UNW_TDEP_IP = UNW_SH_PR,
+    UNW_TDEP_SP = UNW_SH_R15,
+    UNW_TDEP_EH = UNW_SH_R0
+  }
+sh_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   2
+
+typedef ucontext_t unw_tdep_context_t;
+
+#define unw_tdep_getcontext(uc)                (getcontext (uc), 0)
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no sh-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-x86.h b/external/android-libunwind/include/libunwind-x86.h
new file mode 100644 (file)
index 0000000..e46632d
--- /dev/null
@@ -0,0 +1,193 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2002-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <sys/types.h>
+#include <inttypes.h>
+#include <ucontext.h>
+
+#define UNW_TARGET     x86
+#define UNW_TARGET_X86 1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+#define UNW_TDEP_CURSOR_LEN    127
+
+typedef uint32_t unw_word_t;
+typedef int32_t unw_sword_t;
+
+typedef union {
+  struct { uint8_t b[4]; } val32;
+  struct { uint8_t b[10]; } val80;
+  struct { uint8_t b[16]; } val128;
+} unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    /* Note: general registers are expected to start with index 0.
+       This convention facilitates architecture-independent
+       implementation of the C++ exception handling ABI.  See
+       _Unwind_SetGR() and _Unwind_GetGR() for details.
+
+       The described register usage convention is based on "System V
+       Application Binary Interface, Intel386 Architecture Processor
+       Supplement, Fourth Edition" at
+
+         http://www.linuxbase.org/spec/refspecs/elf/abi386-4.pdf
+
+       It would have been nice to use the same register numbering as
+       DWARF, but that doesn't work because the libunwind requires
+       that the exception argument registers be consecutive, which the
+       wouldn't be with the DWARF numbering.  */
+    UNW_X86_EAX,       /* scratch (exception argument 1) */
+    UNW_X86_EDX,       /* scratch (exception argument 2) */
+    UNW_X86_ECX,       /* scratch */
+    UNW_X86_EBX,       /* preserved */
+    UNW_X86_ESI,       /* preserved */
+    UNW_X86_EDI,       /* preserved */
+    UNW_X86_EBP,       /* (optional) frame-register */
+    UNW_X86_ESP,       /* (optional) frame-register */
+    UNW_X86_EIP,       /* frame-register */
+    UNW_X86_EFLAGS,    /* scratch (except for "direction", which is fixed */
+    UNW_X86_TRAPNO,    /* scratch */
+
+    /* MMX/stacked-fp registers */
+    UNW_X86_ST0,       /* fp return value */
+    UNW_X86_ST1,       /* scratch */
+    UNW_X86_ST2,       /* scratch */
+    UNW_X86_ST3,       /* scratch */
+    UNW_X86_ST4,       /* scratch */
+    UNW_X86_ST5,       /* scratch */
+    UNW_X86_ST6,       /* scratch */
+    UNW_X86_ST7,       /* scratch */
+
+    UNW_X86_FCW,       /* scratch */
+    UNW_X86_FSW,       /* scratch */
+    UNW_X86_FTW,       /* scratch */
+    UNW_X86_FOP,       /* scratch */
+    UNW_X86_FCS,       /* scratch */
+    UNW_X86_FIP,       /* scratch */
+    UNW_X86_FEA,       /* scratch */
+    UNW_X86_FDS,       /* scratch */
+
+    /* SSE registers */
+    UNW_X86_XMM0_lo,   /* scratch */
+    UNW_X86_XMM0_hi,   /* scratch */
+    UNW_X86_XMM1_lo,   /* scratch */
+    UNW_X86_XMM1_hi,   /* scratch */
+    UNW_X86_XMM2_lo,   /* scratch */
+    UNW_X86_XMM2_hi,   /* scratch */
+    UNW_X86_XMM3_lo,   /* scratch */
+    UNW_X86_XMM3_hi,   /* scratch */
+    UNW_X86_XMM4_lo,   /* scratch */
+    UNW_X86_XMM4_hi,   /* scratch */
+    UNW_X86_XMM5_lo,   /* scratch */
+    UNW_X86_XMM5_hi,   /* scratch */
+    UNW_X86_XMM6_lo,   /* scratch */
+    UNW_X86_XMM6_hi,   /* scratch */
+    UNW_X86_XMM7_lo,   /* scratch */
+    UNW_X86_XMM7_hi,   /* scratch */
+
+    UNW_X86_MXCSR,     /* scratch */
+
+    /* segment registers */
+    UNW_X86_GS,                /* special */
+    UNW_X86_FS,                /* special */
+    UNW_X86_ES,                /* special */
+    UNW_X86_DS,                /* special */
+    UNW_X86_SS,                /* special */
+    UNW_X86_CS,                /* special */
+    UNW_X86_TSS,       /* special */
+    UNW_X86_LDT,       /* special */
+
+    /* frame info (read-only) */
+    UNW_X86_CFA,
+
+    UNW_X86_XMM0,      /* scratch */
+    UNW_X86_XMM1,      /* scratch */
+    UNW_X86_XMM2,      /* scratch */
+    UNW_X86_XMM3,      /* scratch */
+    UNW_X86_XMM4,      /* scratch */
+    UNW_X86_XMM5,      /* scratch */
+    UNW_X86_XMM6,      /* scratch */
+    UNW_X86_XMM7,      /* scratch */
+
+    UNW_TDEP_LAST_REG = UNW_X86_XMM7,
+
+    UNW_TDEP_IP = UNW_X86_EIP,
+    UNW_TDEP_SP = UNW_X86_ESP,
+    UNW_TDEP_EH = UNW_X86_EAX
+  }
+x86_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   2       /* eax and edx are exception args */
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On x86, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+#include "libunwind-dynamic.h"
+
+typedef struct
+  {
+    /* no x86-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-common.h"
+
+#define unw_tdep_getcontext            UNW_ARCH_OBJ(getcontext)
+extern int unw_tdep_getcontext (unw_tdep_context_t *);
+
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind-x86_64.h b/external/android-libunwind/include/libunwind-x86_64.h
new file mode 100644 (file)
index 0000000..ed8cb11
--- /dev/null
@@ -0,0 +1,145 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2002-2004 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+   Modified for x86_64 by Max Asbock <masbock@us.ibm.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef LIBUNWIND_H
+#define LIBUNWIND_H
+
+#if defined(__cplusplus) || defined(c_plusplus)
+extern "C" {
+#endif
+
+#include <sys/types.h>
+#include <inttypes.h>
+#include <ucontext.h>
+
+#define UNW_TARGET             x86_64
+#define UNW_TARGET_X86_64      1
+
+#define _U_TDEP_QP_TRUE        0       /* see libunwind-dynamic.h  */
+
+/* This needs to be big enough to accommodate "struct cursor", while
+   leaving some slack for future expansion.  Changing this value will
+   require recompiling all users of this library.  Stack allocation is
+   relatively cheap and unwind-state copying is relatively rare, so we
+   want to err on making it rather too big than too small.  */
+#define UNW_TDEP_CURSOR_LEN    127
+
+typedef uint64_t unw_word_t;
+typedef int64_t unw_sword_t;
+
+typedef long double unw_tdep_fpreg_t;
+
+typedef enum
+  {
+    UNW_X86_64_RAX,
+    UNW_X86_64_RDX,
+    UNW_X86_64_RCX,
+    UNW_X86_64_RBX,
+    UNW_X86_64_RSI,
+    UNW_X86_64_RDI,
+    UNW_X86_64_RBP,
+    UNW_X86_64_RSP,
+    UNW_X86_64_R8,
+    UNW_X86_64_R9,
+    UNW_X86_64_R10,
+    UNW_X86_64_R11,
+    UNW_X86_64_R12,
+    UNW_X86_64_R13,
+    UNW_X86_64_R14,
+    UNW_X86_64_R15,
+    UNW_X86_64_RIP,
+#ifdef CONFIG_MSABI_SUPPORT
+    UNW_X86_64_XMM0,
+    UNW_X86_64_XMM1,
+    UNW_X86_64_XMM2,
+    UNW_X86_64_XMM3,
+    UNW_X86_64_XMM4,
+    UNW_X86_64_XMM5,
+    UNW_X86_64_XMM6,
+    UNW_X86_64_XMM7,
+    UNW_X86_64_XMM8,
+    UNW_X86_64_XMM9,
+    UNW_X86_64_XMM10,
+    UNW_X86_64_XMM11,
+    UNW_X86_64_XMM12,
+    UNW_X86_64_XMM13,
+    UNW_X86_64_XMM14,
+    UNW_X86_64_XMM15,
+    UNW_TDEP_LAST_REG = UNW_X86_64_XMM15,
+#else
+    UNW_TDEP_LAST_REG = UNW_X86_64_RIP,
+#endif
+
+    /* XXX Add other regs here */
+
+    /* frame info (read-only) */
+    UNW_X86_64_CFA,
+
+    UNW_TDEP_IP = UNW_X86_64_RIP,
+    UNW_TDEP_SP = UNW_X86_64_RSP,
+    UNW_TDEP_BP = UNW_X86_64_RBP,
+    UNW_TDEP_EH = UNW_X86_64_RAX
+  }
+x86_64_regnum_t;
+
+#define UNW_TDEP_NUM_EH_REGS   2       /* XXX Not sure what this means */
+
+typedef struct unw_tdep_save_loc
+  {
+    /* Additional target-dependent info on a save location.  */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_save_loc_t;
+
+/* On x86_64, we can directly use ucontext_t as the unwind context.  */
+typedef ucontext_t unw_tdep_context_t;
+
+typedef struct
+  {
+    /* no x86-64-specific auxiliary proc-info */
+    /* ANDROID support update. */
+    char __reserved;
+    /* End of ANDROID update. */
+  }
+unw_tdep_proc_info_t;
+
+#include "libunwind-dynamic.h"
+#include "libunwind-common.h"
+
+#define unw_tdep_getcontext            UNW_ARCH_OBJ(getcontext)
+#define unw_tdep_is_fpreg              UNW_ARCH_OBJ(is_fpreg)
+
+extern int unw_tdep_getcontext (unw_tdep_context_t *);
+extern int unw_tdep_is_fpreg (int);
+
+#if defined(__cplusplus) || defined(c_plusplus)
+}
+#endif
+
+#endif /* LIBUNWIND_H */
diff --git a/external/android-libunwind/include/libunwind.h b/external/android-libunwind/include/libunwind.h
new file mode 100644 (file)
index 0000000..0fafda6
--- /dev/null
@@ -0,0 +1,34 @@
+/* Provide a real file - not a symlink - as it would cause multiarch conflicts
+   when multiple different arch releases are installed simultaneously.  */
+
+#ifndef UNW_REMOTE_ONLY
+
+#if defined __aarch64__
+#include "libunwind-aarch64.h"
+#elif defined __arm__
+# include "libunwind-arm.h"
+#elif defined __hppa__
+# include "libunwind-hppa.h"
+#elif defined __ia64__
+# include "libunwind-ia64.h"
+#elif defined __mips__
+# include "libunwind-mips.h"
+#elif defined __powerpc__ && !defined __powerpc64__
+# include "libunwind-ppc32.h"
+#elif defined __powerpc64__
+# include "libunwind-ppc64.h"
+#elif defined __sh__
+# include "libunwind-sh.h"
+#elif defined __i386__
+# include "libunwind-x86.h"
+#elif defined __x86_64__
+# include "libunwind-x86_64.h"
+#else
+# error "Unsupported arch"
+#endif
+
+#else /* UNW_REMOTE_ONLY */
+
+# include "libunwind-arm.h"
+
+#endif /* UNW_REMOTE_ONLY */
diff --git a/external/android-libunwind/include/unwind.h b/external/android-libunwind/include/unwind.h
new file mode 100644 (file)
index 0000000..f8d43d0
--- /dev/null
@@ -0,0 +1,154 @@
+/* libunwind - a platform-independent unwind library
+   Copyright (C) 2003 Hewlett-Packard Co
+       Contributed by David Mosberger-Tang <davidm@hpl.hp.com>
+
+This file is part of libunwind.
+
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.  */
+
+#ifndef _UNWIND_H
+#define _UNWIND_H
+
+/* For uint64_t */
+#include <stdint.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/* Minimal interface as per C++ ABI draft standard:
+
+       http://www.codesourcery.com/cxx-abi/abi-eh.html */
+
+typedef enum
+  {
+    _URC_NO_REASON = 0,
+    _URC_FOREIGN_EXCEPTION_CAUGHT = 1,
+    _URC_FATAL_PHASE2_ERROR = 2,
+    _URC_FATAL_PHASE1_ERROR = 3,
+    _URC_NORMAL_STOP = 4,
+    _URC_END_OF_STACK = 5,
+    _URC_HANDLER_FOUND = 6,
+    _URC_INSTALL_CONTEXT = 7,
+    _URC_CONTINUE_UNWIND = 8
+  }
+_Unwind_Reason_Code;
+
+typedef int _Unwind_Action;
+
+#define _UA_SEARCH_PHASE       1
+#define _UA_CLEANUP_PHASE      2
+#define _UA_HANDLER_FRAME      4
+#define _UA_FORCE_UNWIND       8
+
+struct _Unwind_Context;                /* opaque data-structure */
+struct _Unwind_Exception;      /* forward-declaration */
+
+typedef void (*_Unwind_Exception_Cleanup_Fn) (_Unwind_Reason_Code,
+                                             struct _Unwind_Exception *);
+
+typedef _Unwind_Reason_Code (*_Unwind_Stop_Fn) (int, _Unwind_Action,
+                                               uint64_t,
+                                               struct _Unwind_Exception *,
+                                               struct _Unwind_Context *,
+                                               void *);
+
+/* The C++ ABI requires exception_class, private_1, and private_2 to
+   be of type uint64 and the entire structure to be
+   double-word-aligned. Please note that exception_class stays 64-bit 
+   even on 32-bit machines for gcc compatibility.  */
+struct _Unwind_Exception
+  {
+    uint64_t exception_class;
+    _Unwind_Exception_Cleanup_Fn exception_cleanup;
+    unsigned long private_1;
+    unsigned long private_2;
+  } __attribute__((__aligned__));
+
+extern _Unwind_Reason_Code _Unwind_RaiseException (struct _Unwind_Exception *);
+extern _Unwind_Reason_Code _Unwind_ForcedUnwind (struct _Unwind_Exception *,
+                                                _Unwind_Stop_Fn, void *);
+extern void _Unwind_Resume (struct _Unwind_Exception *);
+extern void _Unwind_DeleteException (struct _Unwind_Exception *);
+extern unsigned long _Unwind_GetGR (struct _Unwind_Context *, int);
+extern void _Unwind_SetGR (struct _Unwind_Context *, int, unsigned long);
+extern unsigned long _Unwind_GetIP (struct _Unwind_Context *);
+extern unsigned long _Unwind_GetIPInfo (struct _Unwind_Context *, int *);
+extern void _Unwind_SetIP (struct _Unwind_Context *, unsigned long);
+extern unsigned long _Unwind_GetLanguageSpecificData (struct _Unwind_Context*);
+extern unsigned long _Unwind_GetRegionStart (struct _Unwind_Context *);
+
+#ifdef _GNU_SOURCE
+
+/* Callback for _Unwind_Backtrace().  The backtrace stops immediately
+   if the callback returns any value other than _URC_NO_REASON. */
+typedef _Unwind_Reason_Code (*_Unwind_Trace_Fn) (struct _Unwind_Context *,
+                                                void *);
+
+/* See http://gcc.gnu.org/ml/gcc-patches/2001-09/msg00082.html for why
+   _UA_END_OF_STACK exists.  */
+# define _UA_END_OF_STACK      16
+
+/* If the unwind was initiated due to a forced unwind, resume that
+   operation, else re-raise the exception.  This is used by
+   __cxa_rethrow().  */
+extern _Unwind_Reason_Code
+         _Unwind_Resume_or_Rethrow (struct _Unwind_Exception *);
+
+/* See http://gcc.gnu.org/ml/gcc-patches/2003-09/msg00154.html for why
+   _Unwind_GetBSP() exists.  */
+extern unsigned long _Unwind_GetBSP (struct _Unwind_Context *);
+
+/* Return the "canonical frame address" for the given context.
+   This is used by NPTL... */
+extern unsigned long _Unwind_GetCFA (struct _Unwind_Context *);
+
+/* Return the base-address for data references.  */
+extern unsigned long _Unwind_GetDataRelBase (struct _Unwind_Context *);
+
+/* Return the base-address for text references.  */
+extern unsigned long _Unwind_GetTextRelBase (struct _Unwind_Context *);
+
+/* Call _Unwind_Trace_Fn once for each stack-frame, without doing any
+   cleanup.  The first frame for which the callback is invoked is the
+   one for the caller of _Unwind_Backtrace().  _Unwind_Backtrace()
+   returns _URC_END_OF_STACK when the backtrace stopped due to
+   reaching the end of the call-chain or _URC_FATAL_PHASE1_ERROR if it
+   stops for any other reason.  */
+extern _Unwind_Reason_Code _Unwind_Backtrace (_Unwind_Trace_Fn, void *);
+
+/* Find the start-address of the procedure containing the specified IP
+   or NULL if it cannot be found (e.g., because the function has no
+   unwind info).  Note: there is not necessarily a one-to-one
+   correspondence between source-level functions and procedures: some
+   functions don't have unwind-info and others are split into multiple
+   procedures.  */
+extern void *_Unwind_FindEnclosingFunction (void *);
+
+/* See also Linux Standard Base Spec:
+    http://www.linuxbase.org/spec/refspecs/LSB_1.3.0/gLSB/gLSB/libgcc-s.html */
+
+#endif /* _GNU_SOURCE */
+
+#ifdef __cplusplus
+};
+#endif
+
+#endif /* _UNWIND_H */
index df1c00441047e7cc439608aa1aa083f585f5ace0..6b3dd0b5a0f5ebd75d4be8070f711805c0f948f1 160000 (submodule)
@@ -1 +1 @@
-Subproject commit df1c00441047e7cc439608aa1aa083f585f5ace0
+Subproject commit 6b3dd0b5a0f5ebd75d4be8070f711805c0f948f1
index ac992abfaf99aa62491ecd302c5e8be34881c022..7f5aa03148da79519f638f1bd93b37cdaa45c539 100644 (file)
@@ -233,10 +233,8 @@ AM_CONDITIONAL(POWERPC_DARWIN,test x$powerpc_darwin = xtrue)
 AC_MSG_CHECKING(for __sync_bool_compare_and_swap)
 AC_TRY_COMPILE([],[
 volatile unsigned int foo = 0;
-int main(int argc, char** argv) {
-    unsigned int r1 = __sync_bool_compare_and_swap(&foo, 0, 1);
-    return 0;
-}
+unsigned int r1 = __sync_bool_compare_and_swap(&foo, 0, 1);
+return 0;
 ], [
 AC_MSG_RESULT(yes)
 AC_DEFINE(HAS___SYNC_BOOL_COMPARE_AND_SWAP)
index f29f4d1601ee83055ad10cd9599067f4042107ab..22ffdeb139ec2c94ebf1a57e7b052ce317bd573f 100644 (file)
@@ -1094,11 +1094,6 @@ find spots that need to be tuned for this mode of operation.   Alternatively,
 this mode can be enabled at compile time by using the --with-cooperative-gc
 flag when calling configure.
 .TP
-\fBMONO_ENABLE_SHM\fR
-Unix only: Enable support for cross-process handles.  Cross-process
-handles are used to expose process handles, thread handles, named
-mutexes, named events and named semaphores across Unix processes.
-.TP
 \fBMONO_ENV_OPTIONS\fR
 This environment variable allows you to pass command line arguments to
 a Mono process through the environment.   This is useful for example
@@ -1513,24 +1508,6 @@ For a complete description of recommended practices for application
 deployment, see
 http://www.mono-project.com/docs/getting-started/application-deployment/
 .TP
-\fBMONO_RTC\fR
-Experimental RTC support in the statistical profiler: if the user has
-the permission, more accurate statistics are gathered.  The MONO_RTC
-value must be restricted to what the Linux rtc allows: power of two
-from 64 to 8192 Hz. To enable higher frequencies like 4096 Hz, run as root:
-.nf
-
-       echo 4096 > /proc/sys/dev/rtc/max-user-freq
-
-.fi
-.Sp
-For example:
-.nf
-
-       MONO_RTC=4096 mono --profiler=default:stat program.exe
-
-.fi
-.TP 
 \fBMONO_SHARED_DIR\fR
 If set its the directory where the ".wapi" handle state is stored.
 This is the directory where the Windows I/O Emulation layer stores its
@@ -1809,6 +1786,10 @@ Enables the maximum JIT verbosity for the specified method. This is
 very helpfull to diagnose a miscompilation problems of a specific
 method.
 .TP
+\fBMONO_JIT_DUMP_METHOD\fR
+Enables sending of the JITs intermediate representation for a specified
+method to the IdealGraphVisualizer tool.
+.TP
 \fBMONO_VERBOSE_HWCAP\fR
 If set, makes the JIT output information about detected CPU features
 (such as SSE, CMOV, FCMOV, etc) to stdout.
index c166333233651b48fb029e11b1ce082876b5b6a6..af61efa37cb84a91b735581972a4f8dec8565285 100644 (file)
@@ -137,9 +137,9 @@ to the control port
 .IP \[bu] 2
 \f[I]sample[=TYPE[/FREQ]]\f[]: collect statistical samples of the
 program behaviour.
-The default is to collect a 1000 times per second the instruction
-pointer.
-This is equivalent to the value \[lq]cycles/1000\[rq] for
+The default is to collect a 100 times per second (100 Hz) the
+instruction pointer.
+This is equivalent to the value \[lq]cycles/100\[rq] for
 \f[I]TYPE\f[].
 On some systems, like with recent Linux kernels, it is possible to
 cause the sampling to happen for other events provided by the
@@ -171,6 +171,24 @@ TIMER can have the following values:
 collect \f[I]NUM\f[] frames at the most.
 The default is 8.
 .IP \[bu] 2
+\f[I]maxsamples=NUM\f[]: stop allocating reusable sample events
+once \f[I]NUM\f[] events have been allocated (a value of zero for
+all intents and purposes means unlimited). By default, the value
+of this setting is the number of CPU cores multiplied by 1000. This
+is usually a good enough value for typical desktop and mobile apps.
+If you're losing too many samples due to this default (which is
+possible in apps with an unusually high amount of threads), you
+may want to tinker with this value to find a good balance between
+sample hit rate and performance impact on the app. The way it works
+is that sample events are enqueued for reuse after they're flushed
+to the output file; if a thread gets a sampling signal but there are
+no sample events in the reuse queue and the profiler has reached the
+maximum number of sample allocations, the sample gets dropped. So a
+higher number for this setting will increase the chance that a
+thread is able to collect a sample, but also necessarily means that
+there will be more work done by the profiler. You can run Mono with
+the \f[I]--stats\f[] option to see statistics about sample events.
+.IP \[bu] 2
 \f[I]calldepth=NUM\f[]: ignore method enter/leave events when the
 call chain depth is bigger than NUM.
 .IP \[bu] 2
diff --git a/mcs/COPYING.LIB b/mcs/COPYING.LIB
deleted file mode 100644 (file)
index 5bc8fb2..0000000
+++ /dev/null
@@ -1,481 +0,0 @@
-                  GNU LIBRARY GENERAL PUBLIC LICENSE
-                       Version 2, June 1991
-
- Copyright (C) 1991 Free Software Foundation, Inc.
- 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
-[This is the first released version of the library GPL.  It is
- numbered 2 because it goes with version 2 of the ordinary GPL.]
-
-                            Preamble
-
-  The licenses for most software are designed to take away your
-freedom to share and change it.  By contrast, the GNU General Public
-Licenses are intended to guarantee your freedom to share and change
-free software--to make sure the software is free for all its users.
-
-  This license, the Library General Public License, applies to some
-specially designated Free Software Foundation software, and to any
-other libraries whose authors decide to use it.  You can use it for
-your libraries, too.
-
-  When we speak of free software, we are referring to freedom, not
-price.  Our General Public Licenses are designed to make sure that you
-have the freedom to distribute copies of free software (and charge for
-this service if you wish), that you receive source code or can get it
-if you want it, that you can change the software or use pieces of it
-in new free programs; and that you know you can do these things.
-
-  To protect your rights, we need to make restrictions that forbid
-anyone to deny you these rights or to ask you to surrender the rights.
-These restrictions translate to certain responsibilities for you if
-you distribute copies of the library, or if you modify it.
-
-  For example, if you distribute copies of the library, whether gratis
-or for a fee, you must give the recipients all the rights that we gave
-you.  You must make sure that they, too, receive or can get the source
-code.  If you link a program with the library, you must provide
-complete object files to the recipients so that they can relink them
-with the library, after making changes to the library and recompiling
-it.  And you must show them these terms so they know their rights.
-
-  Our method of protecting your rights has two steps: (1) copyright
-the library, and (2) offer you this license which gives you legal
-permission to copy, distribute and/or modify the library.
-
-  Also, for each distributor's protection, we want to make certain
-that everyone understands that there is no warranty for this free
-library.  If the library is modified by someone else and passed on, we
-want its recipients to know that what they have is not the original
-version, so that any problems introduced by others will not reflect on
-the original authors' reputations.
-\f
-  Finally, any free program is threatened constantly by software
-patents.  We wish to avoid the danger that companies distributing free
-software will individually obtain patent licenses, thus in effect
-transforming the program into proprietary software.  To prevent this,
-we have made it clear that any patent must be licensed for everyone's
-free use or not licensed at all.
-
-  Most GNU software, including some libraries, is covered by the ordinary
-GNU General Public License, which was designed for utility programs.  This
-license, the GNU Library General Public License, applies to certain
-designated libraries.  This license is quite different from the ordinary
-one; be sure to read it in full, and don't assume that anything in it is
-the same as in the ordinary license.
-
-  The reason we have a separate public license for some libraries is that
-they blur the distinction we usually make between modifying or adding to a
-program and simply using it.  Linking a program with a library, without
-changing the library, is in some sense simply using the library, and is
-analogous to running a utility program or application program.  However, in
-a textual and legal sense, the linked executable is a combined work, a
-derivative of the original library, and the ordinary General Public License
-treats it as such.
-
-  Because of this blurred distinction, using the ordinary General
-Public License for libraries did not effectively promote software
-sharing, because most developers did not use the libraries.  We
-concluded that weaker conditions might promote sharing better.
-
-  However, unrestricted linking of non-free programs would deprive the
-users of those programs of all benefit from the free status of the
-libraries themselves.  This Library General Public License is intended to
-permit developers of non-free programs to use free libraries, while
-preserving your freedom as a user of such programs to change the free
-libraries that are incorporated in them.  (We have not seen how to achieve
-this as regards changes in header files, but we have achieved it as regards
-changes in the actual functions of the Library.)  The hope is that this
-will lead to faster development of free libraries.
-
-  The precise terms and conditions for copying, distribution and
-modification follow.  Pay close attention to the difference between a
-"work based on the library" and a "work that uses the library".  The
-former contains code derived from the library, while the latter only
-works together with the library.
-
-  Note that it is possible for a library to be covered by the ordinary
-General Public License rather than by this special one.
-\f
-                  GNU LIBRARY GENERAL PUBLIC LICENSE
-   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
-  0. This License Agreement applies to any software library which
-contains a notice placed by the copyright holder or other authorized
-party saying it may be distributed under the terms of this Library
-General Public License (also called "this License").  Each licensee is
-addressed as "you".
-
-  A "library" means a collection of software functions and/or data
-prepared so as to be conveniently linked with application programs
-(which use some of those functions and data) to form executables.
-
-  The "Library", below, refers to any such software library or work
-which has been distributed under these terms.  A "work based on the
-Library" means either the Library or any derivative work under
-copyright law: that is to say, a work containing the Library or a
-portion of it, either verbatim or with modifications and/or translated
-straightforwardly into another language.  (Hereinafter, translation is
-included without limitation in the term "modification".)
-
-  "Source code" for a work means the preferred form of the work for
-making modifications to it.  For a library, complete source code means
-all the source code for all modules it contains, plus any associated
-interface definition files, plus the scripts used to control compilation
-and installation of the library.
-
-  Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope.  The act of
-running a program using the Library is not restricted, and output from
-such a program is covered only if its contents constitute a work based
-on the Library (independent of the use of the Library in a tool for
-writing it).  Whether that is true depends on what the Library does
-and what the program that uses the Library does.
-  
-  1. You may copy and distribute verbatim copies of the Library's
-complete source code as you receive it, in any medium, provided that
-you conspicuously and appropriately publish on each copy an
-appropriate copyright notice and disclaimer of warranty; keep intact
-all the notices that refer to this License and to the absence of any
-warranty; and distribute a copy of this License along with the
-Library.
-
-  You may charge a fee for the physical act of transferring a copy,
-and you may at your option offer warranty protection in exchange for a
-fee.
-\f
-  2. You may modify your copy or copies of the Library or any portion
-of it, thus forming a work based on the Library, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
-    a) The modified work must itself be a software library.
-
-    b) You must cause the files modified to carry prominent notices
-    stating that you changed the files and the date of any change.
-
-    c) You must cause the whole of the work to be licensed at no
-    charge to all third parties under the terms of this License.
-
-    d) If a facility in the modified Library refers to a function or a
-    table of data to be supplied by an application program that uses
-    the facility, other than as an argument passed when the facility
-    is invoked, then you must make a good faith effort to ensure that,
-    in the event an application does not supply such function or
-    table, the facility still operates, and performs whatever part of
-    its purpose remains meaningful.
-
-    (For example, a function in a library to compute square roots has
-    a purpose that is entirely well-defined independent of the
-    application.  Therefore, Subsection 2d requires that any
-    application-supplied function or table used by this function must
-    be optional: if the application does not supply it, the square
-    root function must still compute square roots.)
-
-These requirements apply to the modified work as a whole.  If
-identifiable sections of that work are not derived from the Library,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works.  But when you
-distribute the same sections as part of a whole which is a work based
-on the Library, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote
-it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Library.
-
-In addition, mere aggregation of another work not based on the Library
-with the Library (or with a work based on the Library) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
-  3. You may opt to apply the terms of the ordinary GNU General Public
-License instead of this License to a given copy of the Library.  To do
-this, you must alter all the notices that refer to this License, so
-that they refer to the ordinary GNU General Public License, version 2,
-instead of to this License.  (If a newer version than version 2 of the
-ordinary GNU General Public License has appeared, then you can specify
-that version instead if you wish.)  Do not make any other change in
-these notices.
-\f
-  Once this change is made in a given copy, it is irreversible for
-that copy, so the ordinary GNU General Public License applies to all
-subsequent copies and derivative works made from that copy.
-
-  This option is useful when you wish to copy part of the code of
-the Library into a program that is not a library.
-
-  4. You may copy and distribute the Library (or a portion or
-derivative of it, under Section 2) in object code or executable form
-under the terms of Sections 1 and 2 above provided that you accompany
-it with the complete corresponding machine-readable source code, which
-must be distributed under the terms of Sections 1 and 2 above on a
-medium customarily used for software interchange.
-
-  If distribution of object code is made by offering access to copy
-from a designated place, then offering equivalent access to copy the
-source code from the same place satisfies the requirement to
-distribute the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
-  5. A program that contains no derivative of any portion of the
-Library, but is designed to work with the Library by being compiled or
-linked with it, is called a "work that uses the Library".  Such a
-work, in isolation, is not a derivative work of the Library, and
-therefore falls outside the scope of this License.
-
-  However, linking a "work that uses the Library" with the Library
-creates an executable that is a derivative of the Library (because it
-contains portions of the Library), rather than a "work that uses the
-library".  The executable is therefore covered by this License.
-Section 6 states terms for distribution of such executables.
-
-  When a "work that uses the Library" uses material from a header file
-that is part of the Library, the object code for the work may be a
-derivative work of the Library even though the source code is not.
-Whether this is true is especially significant if the work can be
-linked without the Library, or if the work is itself a library.  The
-threshold for this to be true is not precisely defined by law.
-
-  If such an object file uses only numerical parameters, data
-structure layouts and accessors, and small macros and small inline
-functions (ten lines or less in length), then the use of the object
-file is unrestricted, regardless of whether it is legally a derivative
-work.  (Executables containing this object code plus portions of the
-Library will still fall under Section 6.)
-
-  Otherwise, if the work is a derivative of the Library, you may
-distribute the object code for the work under the terms of Section 6.
-Any executables containing that work also fall under Section 6,
-whether or not they are linked directly with the Library itself.
-\f
-  6. As an exception to the Sections above, you may also compile or
-link a "work that uses the Library" with the Library to produce a
-work containing portions of the Library, and distribute that work
-under terms of your choice, provided that the terms permit
-modification of the work for the customer's own use and reverse
-engineering for debugging such modifications.
-
-  You must give prominent notice with each copy of the work that the
-Library is used in it and that the Library and its use are covered by
-this License.  You must supply a copy of this License.  If the work
-during execution displays copyright notices, you must include the
-copyright notice for the Library among them, as well as a reference
-directing the user to the copy of this License.  Also, you must do one
-of these things:
-
-    a) Accompany the work with the complete corresponding
-    machine-readable source code for the Library including whatever
-    changes were used in the work (which must be distributed under
-    Sections 1 and 2 above); and, if the work is an executable linked
-    with the Library, with the complete machine-readable "work that
-    uses the Library", as object code and/or source code, so that the
-    user can modify the Library and then relink to produce a modified
-    executable containing the modified Library.  (It is understood
-    that the user who changes the contents of definitions files in the
-    Library will not necessarily be able to recompile the application
-    to use the modified definitions.)
-
-    b) Accompany the work with a written offer, valid for at
-    least three years, to give the same user the materials
-    specified in Subsection 6a, above, for a charge no more
-    than the cost of performing this distribution.
-
-    c) If distribution of the work is made by offering access to copy
-    from a designated place, offer equivalent access to copy the above
-    specified materials from the same place.
-
-    d) Verify that the user has already received a copy of these
-    materials or that you have already sent this user a copy.
-
-  For an executable, the required form of the "work that uses the
-Library" must include any data and utility programs needed for
-reproducing the executable from it.  However, as a special exception,
-the source code distributed need not include anything that is normally
-distributed (in either source or binary form) with the major
-components (compiler, kernel, and so on) of the operating system on
-which the executable runs, unless that component itself accompanies
-the executable.
-
-  It may happen that this requirement contradicts the license
-restrictions of other proprietary libraries that do not normally
-accompany the operating system.  Such a contradiction means you cannot
-use both them and the Library together in an executable that you
-distribute.
-\f
-  7. You may place library facilities that are a work based on the
-Library side-by-side in a single library together with other library
-facilities not covered by this License, and distribute such a combined
-library, provided that the separate distribution of the work based on
-the Library and of the other library facilities is otherwise
-permitted, and provided that you do these two things:
-
-    a) Accompany the combined library with a copy of the same work
-    based on the Library, uncombined with any other library
-    facilities.  This must be distributed under the terms of the
-    Sections above.
-
-    b) Give prominent notice with the combined library of the fact
-    that part of it is a work based on the Library, and explaining
-    where to find the accompanying uncombined form of the same work.
-
-  8. You may not copy, modify, sublicense, link with, or distribute
-the Library except as expressly provided under this License.  Any
-attempt otherwise to copy, modify, sublicense, link with, or
-distribute the Library is void, and will automatically terminate your
-rights under this License.  However, parties who have received copies,
-or rights, from you under this License will not have their licenses
-terminated so long as such parties remain in full compliance.
-
-  9. You are not required to accept this License, since you have not
-signed it.  However, nothing else grants you permission to modify or
-distribute the Library or its derivative works.  These actions are
-prohibited by law if you do not accept this License.  Therefore, by
-modifying or distributing the Library (or any work based on the
-Library), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Library or works based on it.
-
-  10. Each time you redistribute the Library (or any work based on the
-Library), the recipient automatically receives a license from the
-original licensor to copy, distribute, link with or modify the Library
-subject to these terms and conditions.  You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties to
-this License.
-\f
-  11. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License.  If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Library at all.  For example, if a patent
-license would not permit royalty-free redistribution of the Library by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Library.
-
-If any portion of this section is held invalid or unenforceable under any
-particular circumstance, the balance of the section is intended to apply,
-and the section as a whole is intended to apply in other circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system which is
-implemented by public license practices.  Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
-  12. If the distribution and/or use of the Library is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Library under this License may add
-an explicit geographical distribution limitation excluding those countries,
-so that distribution is permitted only in or among countries not thus
-excluded.  In such case, this License incorporates the limitation as if
-written in the body of this License.
-
-  13. The Free Software Foundation may publish revised and/or new
-versions of the Library General Public License from time to time.
-Such new versions will be similar in spirit to the present version,
-but may differ in detail to address new problems or concerns.
-
-Each version is given a distinguishing version number.  If the Library
-specifies a version number of this License which applies to it and
-"any later version", you have the option of following the terms and
-conditions either of that version or of any later version published by
-the Free Software Foundation.  If the Library does not specify a
-license version number, you may choose any version ever published by
-the Free Software Foundation.
-\f
-  14. If you wish to incorporate parts of the Library into other free
-programs whose distribution conditions are incompatible with these,
-write to the author to ask for permission.  For software which is
-copyrighted by the Free Software Foundation, write to the Free
-Software Foundation; we sometimes make exceptions for this.  Our
-decision will be guided by the two goals of preserving the free status
-of all derivatives of our free software and of promoting the sharing
-and reuse of software generally.
-
-                            NO WARRANTY
-
-  15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
-WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
-EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
-OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
-KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
-IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
-PURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
-LIBRARY IS WITH YOU.  SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
-THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
-
-  16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
-WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
-AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
-FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
-CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
-LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
-RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
-FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
-SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
-DAMAGES.
-
-                     END OF TERMS AND CONDITIONS
-\f
-           How to Apply These Terms to Your New Libraries
-
-  If you develop a new library, and you want it to be of the greatest
-possible use to the public, we recommend making it free software that
-everyone can redistribute and change.  You can do so by permitting
-redistribution under these terms (or, alternatively, under the terms of the
-ordinary General Public License).
-
-  To apply these terms, attach the following notices to the library.  It is
-safest to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least the
-"copyright" line and a pointer to where the full notice is found.
-
-    <one line to give the library's name and a brief idea of what it does.>
-    Copyright (C) <year>  <name of author>
-
-    This library is free software; you can redistribute it and/or
-    modify it under the terms of the GNU Library General Public
-    License as published by the Free Software Foundation; either
-    version 2 of the License, or (at your option) any later version.
-
-    This library 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
-    Library General Public License for more details.
-
-    You should have received a copy of the GNU Library General Public
-    License along with this library; if not, write to the Free Software
-    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
-
-Also add information on how to contact you by electronic and paper mail.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the library, if
-necessary.  Here is a sample; alter the names:
-
-  Yoyodyne, Inc., hereby disclaims all copyright interest in the
-  library `Frob' (a library for tweaking knobs) written by James Random Hacker.
-
-  <signature of Ty Coon>, 1 April 1990
-  Ty Coon, President of Vice
-
-That's all there is to it!
diff --git a/mcs/LICENSE b/mcs/LICENSE
deleted file mode 100644 (file)
index ed2d1fc..0000000
+++ /dev/null
@@ -1,36 +0,0 @@
-
-The Mono code under the mcs/ directory is licensed under various
-different licenses:
-
-       GNU GPL: details avaliable in the file LICENSE.GPL
-       GNU LGPL: details available in the file LICENSE.LGPL
-       MIT X11: text available in the file MIT.X11
-       MPL: text available in the file LICENSE.MPL
-
-       For your convenience copies of the GNU GPL and GNU LGPL are
-       located in the file COPYING and COPYING.LIB.
-
-       * Class Libraries:
-
-               All of the core classes licensed under the terms of
-               the MIT X11 license.
-
-               Third party libraries that we distribute for
-               convenience reasons are distributed under their own
-               terms (all of them allow development of proprietary
-               applications with them).
-
-               Third party libraries include: ByteFX.Data,
-               ICSharpCode.SharpZipLib, Npgsql, MicrosoftAjaxLibrary.
-
-               The Microsoft.JScript assembly is covered by the
-               MIT X11 and the Mozilla MPL license as it contains
-               ported pieces of code from Rhino, the Mozilla JavaScript
-               implementations
-
-       * Mono C# compiler: Dual licensed MIT X11 and GNU GPL.
-
-       * Mono Basic compiler: GNU GPL.
-
-       * Various tools in the `tools' directory: GNU GPL.
-
diff --git a/mcs/LICENSE.CC b/mcs/LICENSE.CC
deleted file mode 100644 (file)
index 6114753..0000000
+++ /dev/null
@@ -1,31 +0,0 @@
-// Copyright 2006 James Newton-King
-// http://www.newtonsoft.com
-//
-// This work is licensed under the Creative Commons Attribution 2.5 License
-// http://creativecommons.org/licenses/by/2.5/
-//
-// You are free:
-//    * to copy, distribute, display, and perform the work
-//    * to make derivative works
-//    * to make commercial use of the work
-//
-// Under the following conditions:
-//    * For any reuse or distribution, you must make clear to others the license terms of this work.
-//    * Any of these conditions can be waived if you get permission from the copyright holder.
-
-From: james.newtonking@gmail.com [mailto:james.newtonking@gmail.com] On Behalf Of James Newton-King
-Sent: Tuesday, June 05, 2007 6:36 AM
-To: Konstantin Triger
-Subject: Re: Support request by Konstantin Triger for Json.NET
-
-Hey Kosta
-
-I think it would be awesome to use Json.NET in Mono for System.Web.Extensions.
-
-The CC license has the following clause: Any of the above conditions can be waived if you get permission from the copyright holder.
-
-I can waive that statement for you and Mono. Would that be acceptable? 
-
-
-Regards,
-James
diff --git a/mcs/LICENSE.GPL b/mcs/LICENSE.GPL
deleted file mode 100644 (file)
index b236c56..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-    Mono compilers and tools.
-    Copyright (C) 2001, 2002, 2003, Ximian and contributors.
-
-    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; 
-
-    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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
diff --git a/mcs/LICENSE.LGPL b/mcs/LICENSE.LGPL
deleted file mode 100644 (file)
index 7447504..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-    Mono class libraries
-    Copyright (C) Mono project (authors listed in individual ChangeLog entries)
-
-    This library is free software; you can redistribute it and/or
-    modify it under the terms of the GNU Library General Public
-    License as published by the Free Software Foundation.
-
-    This library 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
-    Library General Public License for more details.
-
-    You should have received a copy of the GNU Library General Public
-    License along with this library; if not, write to the Free
-    Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
diff --git a/mcs/LICENSE.MPL b/mcs/LICENSE.MPL
deleted file mode 100644 (file)
index 7714141..0000000
+++ /dev/null
@@ -1,470 +0,0 @@
-                          MOZILLA PUBLIC LICENSE
-                                Version 1.1
-
-                              ---------------
-
-1. Definitions.
-
-     1.0.1. "Commercial Use" means distribution or otherwise making the
-     Covered Code available to a third party.
-
-     1.1. "Contributor" means each entity that creates or contributes to
-     the creation of Modifications.
-
-     1.2. "Contributor Version" means the combination of the Original
-     Code, prior Modifications used by a Contributor, and the Modifications
-     made by that particular Contributor.
-
-     1.3. "Covered Code" means the Original Code or Modifications or the
-     combination of the Original Code and Modifications, in each case
-     including portions thereof.
-
-     1.4. "Electronic Distribution Mechanism" means a mechanism generally
-     accepted in the software development community for the electronic
-     transfer of data.
-
-     1.5. "Executable" means Covered Code in any form other than Source
-     Code.
-
-     1.6. "Initial Developer" means the individual or entity identified
-     as the Initial Developer in the Source Code notice required by Exhibit
-     A.
-
-     1.7. "Larger Work" means a work which combines Covered Code or
-     portions thereof with code not governed by the terms of this License.
-
-     1.8. "License" means this document.
-
-     1.8.1. "Licensable" means having the right to grant, to the maximum
-     extent possible, whether at the time of the initial grant or
-     subsequently acquired, any and all of the rights conveyed herein.
-
-     1.9. "Modifications" means any addition to or deletion from the
-     substance or structure of either the Original Code or any previous
-     Modifications. When Covered Code is released as a series of files, a
-     Modification is:
-          A. Any addition to or deletion from the contents of a file
-          containing Original Code or previous Modifications.
-
-          B. Any new file that contains any part of the Original Code or
-          previous Modifications.
-
-     1.10. "Original Code" means Source Code of computer software code
-     which is described in the Source Code notice required by Exhibit A as
-     Original Code, and which, at the time of its release under this
-     License is not already Covered Code governed by this License.
-
-     1.10.1. "Patent Claims" means any patent claim(s), now owned or
-     hereafter acquired, including without limitation,  method, process,
-     and apparatus claims, in any patent Licensable by grantor.
-
-     1.11. "Source Code" means the preferred form of the Covered Code for
-     making modifications to it, including all modules it contains, plus
-     any associated interface definition files, scripts used to control
-     compilation and installation of an Executable, or source code
-     differential comparisons against either the Original Code or another
-     well known, available Covered Code of the Contributor's choice. The
-     Source Code can be in a compressed or archival form, provided the
-     appropriate decompression or de-archiving software is widely available
-     for no charge.
-
-     1.12. "You" (or "Your")  means an individual or a legal entity
-     exercising rights under, and complying with all of the terms of, this
-     License or a future version of this License issued under Section 6.1.
-     For legal entities, "You" includes any entity which controls, is
-     controlled by, or is under common control with You. For purposes of
-     this definition, "control" means (a) the power, direct or indirect,
-     to cause the direction or management of such entity, whether by
-     contract or otherwise, or (b) ownership of more than fifty percent
-     (50%) of the outstanding shares or beneficial ownership of such
-     entity.
-
-2. Source Code License.
-
-     2.1. The Initial Developer Grant.
-     The Initial Developer hereby grants You a world-wide, royalty-free,
-     non-exclusive license, subject to third party intellectual property
-     claims:
-          (a)  under intellectual property rights (other than patent or
-          trademark) Licensable by Initial Developer to use, reproduce,
-          modify, display, perform, sublicense and distribute the Original
-          Code (or portions thereof) with or without Modifications, and/or
-          as part of a Larger Work; and
-
-          (b) under Patents Claims infringed by the making, using or
-          selling of Original Code, to make, have made, use, practice,
-          sell, and offer for sale, and/or otherwise dispose of the
-          Original Code (or portions thereof).
-
-          (c) the licenses granted in this Section 2.1(a) and (b) are
-          effective on the date Initial Developer first distributes
-          Original Code under the terms of this License.
-
-          (d) Notwithstanding Section 2.1(b) above, no patent license is
-          granted: 1) for code that You delete from the Original Code; 2)
-          separate from the Original Code;  or 3) for infringements caused
-          by: i) the modification of the Original Code or ii) the
-          combination of the Original Code with other software or devices.
-
-     2.2. Contributor Grant.
-     Subject to third party intellectual property claims, each Contributor
-     hereby grants You a world-wide, royalty-free, non-exclusive license
-
-          (a)  under intellectual property rights (other than patent or
-          trademark) Licensable by Contributor, to use, reproduce, modify,
-          display, perform, sublicense and distribute the Modifications
-          created by such Contributor (or portions thereof) either on an
-          unmodified basis, with other Modifications, as Covered Code
-          and/or as part of a Larger Work; and
-
-          (b) under Patent Claims infringed by the making, using, or
-          selling of  Modifications made by that Contributor either alone
-          and/or in combination with its Contributor Version (or portions
-          of such combination), to make, use, sell, offer for sale, have
-          made, and/or otherwise dispose of: 1) Modifications made by that
-          Contributor (or portions thereof); and 2) the combination of
-          Modifications made by that Contributor with its Contributor
-          Version (or portions of such combination).
-
-          (c) the licenses granted in Sections 2.2(a) and 2.2(b) are
-          effective on the date Contributor first makes Commercial Use of
-          the Covered Code.
-
-          (d)    Notwithstanding Section 2.2(b) above, no patent license is
-          granted: 1) for any code that Contributor has deleted from the
-          Contributor Version; 2)  separate from the Contributor Version;
-          3)  for infringements caused by: i) third party modifications of
-          Contributor Version or ii)  the combination of Modifications made
-          by that Contributor with other software  (except as part of the
-          Contributor Version) or other devices; or 4) under Patent Claims
-          infringed by Covered Code in the absence of Modifications made by
-          that Contributor.
-
-3. Distribution Obligations.
-
-     3.1. Application of License.
-     The Modifications which You create or to which You contribute are
-     governed by the terms of this License, including without limitation
-     Section 2.2. The Source Code version of Covered Code may be
-     distributed only under the terms of this License or a future version
-     of this License released under Section 6.1, and You must include a
-     copy of this License with every copy of the Source Code You
-     distribute. You may not offer or impose any terms on any Source Code
-     version that alters or restricts the applicable version of this
-     License or the recipients' rights hereunder. However, You may include
-     an additional document offering the additional rights described in
-     Section 3.5.
-
-     3.2. Availability of Source Code.
-     Any Modification which You create or to which You contribute must be
-     made available in Source Code form under the terms of this License
-     either on the same media as an Executable version or via an accepted
-     Electronic Distribution Mechanism to anyone to whom you made an
-     Executable version available; and if made available via Electronic
-     Distribution Mechanism, must remain available for at least twelve (12)
-     months after the date it initially became available, or at least six
-     (6) months after a subsequent version of that particular Modification
-     has been made available to such recipients. You are responsible for
-     ensuring that the Source Code version remains available even if the
-     Electronic Distribution Mechanism is maintained by a third party.
-
-     3.3. Description of Modifications.
-     You must cause all Covered Code to which You contribute to contain a
-     file documenting the changes You made to create that Covered Code and
-     the date of any change. You must include a prominent statement that
-     the Modification is derived, directly or indirectly, from Original
-     Code provided by the Initial Developer and including the name of the
-     Initial Developer in (a) the Source Code, and (b) in any notice in an
-     Executable version or related documentation in which You describe the
-     origin or ownership of the Covered Code.
-
-     3.4. Intellectual Property Matters
-          (a) Third Party Claims.
-          If Contributor has knowledge that a license under a third party's
-          intellectual property rights is required to exercise the rights
-          granted by such Contributor under Sections 2.1 or 2.2,
-          Contributor must include a text file with the Source Code
-          distribution titled "LEGAL" which describes the claim and the
-          party making the claim in sufficient detail that a recipient will
-          know whom to contact. If Contributor obtains such knowledge after
-          the Modification is made available as described in Section 3.2,
-          Contributor shall promptly modify the LEGAL file in all copies
-          Contributor makes available thereafter and shall take other steps
-          (such as notifying appropriate mailing lists or newsgroups)
-          reasonably calculated to inform those who received the Covered
-          Code that new knowledge has been obtained.
-
-          (b) Contributor APIs.
-          If Contributor's Modifications include an application programming
-          interface and Contributor has knowledge of patent licenses which
-          are reasonably necessary to implement that API, Contributor must
-          also include this information in the LEGAL file.
-
-               (c)    Representations.
-          Contributor represents that, except as disclosed pursuant to
-          Section 3.4(a) above, Contributor believes that Contributor's
-          Modifications are Contributor's original creation(s) and/or
-          Contributor has sufficient rights to grant the rights conveyed by
-          this License.
-
-     3.5. Required Notices.
-     You must duplicate the notice in Exhibit A in each file of the Source
-     Code.  If it is not possible to put such notice in a particular Source
-     Code file due to its structure, then You must include such notice in a
-     location (such as a relevant directory) where a user would be likely
-     to look for such a notice.  If You created one or more Modification(s)
-     You may add your name as a Contributor to the notice described in
-     Exhibit A.  You must also duplicate this License in any documentation
-     for the Source Code where You describe recipients' rights or ownership
-     rights relating to Covered Code.  You may choose to offer, and to
-     charge a fee for, warranty, support, indemnity or liability
-     obligations to one or more recipients of Covered Code. However, You
-     may do so only on Your own behalf, and not on behalf of the Initial
-     Developer or any Contributor. You must make it absolutely clear than
-     any such warranty, support, indemnity or liability obligation is
-     offered by You alone, and You hereby agree to indemnify the Initial
-     Developer and every Contributor for any liability incurred by the
-     Initial Developer or such Contributor as a result of warranty,
-     support, indemnity or liability terms You offer.
-
-     3.6. Distribution of Executable Versions.
-     You may distribute Covered Code in Executable form only if the
-     requirements of Section 3.1-3.5 have been met for that Covered Code,
-     and if You include a notice stating that the Source Code version of
-     the Covered Code is available under the terms of this License,
-     including a description of how and where You have fulfilled the
-     obligations of Section 3.2. The notice must be conspicuously included
-     in any notice in an Executable version, related documentation or
-     collateral in which You describe recipients' rights relating to the
-     Covered Code. You may distribute the Executable version of Covered
-     Code or ownership rights under a license of Your choice, which may
-     contain terms different from this License, provided that You are in
-     compliance with the terms of this License and that the license for the
-     Executable version does not attempt to limit or alter the recipient's
-     rights in the Source Code version from the rights set forth in this
-     License. If You distribute the Executable version under a different
-     license You must make it absolutely clear that any terms which differ
-     from this License are offered by You alone, not by the Initial
-     Developer or any Contributor. You hereby agree to indemnify the
-     Initial Developer and every Contributor for any liability incurred by
-     the Initial Developer or such Contributor as a result of any such
-     terms You offer.
-
-     3.7. Larger Works.
-     You may create a Larger Work by combining Covered Code with other code
-     not governed by the terms of this License and distribute the Larger
-     Work as a single product. In such a case, You must make sure the
-     requirements of this License are fulfilled for the Covered Code.
-
-4. Inability to Comply Due to Statute or Regulation.
-
-     If it is impossible for You to comply with any of the terms of this
-     License with respect to some or all of the Covered Code due to
-     statute, judicial order, or regulation then You must: (a) comply with
-     the terms of this License to the maximum extent possible; and (b)
-     describe the limitations and the code they affect. Such description
-     must be included in the LEGAL file described in Section 3.4 and must
-     be included with all distributions of the Source Code. Except to the
-     extent prohibited by statute or regulation, such description must be
-     sufficiently detailed for a recipient of ordinary skill to be able to
-     understand it.
-
-5. Application of this License.
-
-     This License applies to code to which the Initial Developer has
-     attached the notice in Exhibit A and to related Covered Code.
-
-6. Versions of the License.
-
-     6.1. New Versions.
-     Netscape Communications Corporation ("Netscape") may publish revised
-     and/or new versions of the License from time to time. Each version
-     will be given a distinguishing version number.
-
-     6.2. Effect of New Versions.
-     Once Covered Code has been published under a particular version of the
-     License, You may always continue to use it under the terms of that
-     version. You may also choose to use such Covered Code under the terms
-     of any subsequent version of the License published by Netscape. No one
-     other than Netscape has the right to modify the terms applicable to
-     Covered Code created under this License.
-
-     6.3. Derivative Works.
-     If You create or use a modified version of this License (which you may
-     only do in order to apply it to code which is not already Covered Code
-     governed by this License), You must (a) rename Your license so that
-     the phrases "Mozilla", "MOZILLAPL", "MOZPL", "Netscape",
-     "MPL", "NPL" or any confusingly similar phrase do not appear in your
-     license (except to note that your license differs from this License)
-     and (b) otherwise make it clear that Your version of the license
-     contains terms which differ from the Mozilla Public License and
-     Netscape Public License. (Filling in the name of the Initial
-     Developer, Original Code or Contributor in the notice described in
-     Exhibit A shall not of themselves be deemed to be modifications of
-     this License.)
-
-7. DISCLAIMER OF WARRANTY.
-
-     COVERED CODE IS PROVIDED UNDER THIS LICENSE ON AN "AS IS" BASIS,
-     WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING,
-     WITHOUT LIMITATION, WARRANTIES THAT THE COVERED CODE IS FREE OF
-     DEFECTS, MERCHANTABLE, FIT FOR A PARTICULAR PURPOSE OR NON-INFRINGING.
-     THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE COVERED CODE
-     IS WITH YOU. SHOULD ANY COVERED CODE PROVE DEFECTIVE IN ANY RESPECT,
-     YOU (NOT THE INITIAL DEVELOPER OR ANY OTHER CONTRIBUTOR) ASSUME THE
-     COST OF ANY NECESSARY SERVICING, REPAIR OR CORRECTION. THIS DISCLAIMER
-     OF WARRANTY CONSTITUTES AN ESSENTIAL PART OF THIS LICENSE. NO USE OF
-     ANY COVERED CODE IS AUTHORIZED HEREUNDER EXCEPT UNDER THIS DISCLAIMER.
-
-8. TERMINATION.
-
-     8.1.  This License and the rights granted hereunder will terminate
-     automatically if You fail to comply with terms herein and fail to cure
-     such breach within 30 days of becoming aware of the breach. All
-     sublicenses to the Covered Code which are properly granted shall
-     survive any termination of this License. Provisions which, by their
-     nature, must remain in effect beyond the termination of this License
-     shall survive.
-
-     8.2.  If You initiate litigation by asserting a patent infringement
-     claim (excluding declatory judgment actions) against Initial Developer
-     or a Contributor (the Initial Developer or Contributor against whom
-     You file such action is referred to as "Participant")  alleging that:
-
-     (a)  such Participant's Contributor Version directly or indirectly
-     infringes any patent, then any and all rights granted by such
-     Participant to You under Sections 2.1 and/or 2.2 of this License
-     shall, upon 60 days notice from Participant terminate prospectively,
-     unless if within 60 days after receipt of notice You either: (i)
-     agree in writing to pay Participant a mutually agreeable reasonable
-     royalty for Your past and future use of Modifications made by such
-     Participant, or (ii) withdraw Your litigation claim with respect to
-     the Contributor Version against such Participant.  If within 60 days
-     of notice, a reasonable royalty and payment arrangement are not
-     mutually agreed upon in writing by the parties or the litigation claim
-     is not withdrawn, the rights granted by Participant to You under
-     Sections 2.1 and/or 2.2 automatically terminate at the expiration of
-     the 60 day notice period specified above.
-
-     (b)  any software, hardware, or device, other than such Participant's
-     Contributor Version, directly or indirectly infringes any patent, then
-     any rights granted to You by such Participant under Sections 2.1(b)
-     and 2.2(b) are revoked effective as of the date You first made, used,
-     sold, distributed, or had made, Modifications made by that
-     Participant.
-
-     8.3.  If You assert a patent infringement claim against Participant
-     alleging that such Participant's Contributor Version directly or
-     indirectly infringes any patent where such claim is resolved (such as
-     by license or settlement) prior to the initiation of patent
-     infringement litigation, then the reasonable value of the licenses
-     granted by such Participant under Sections 2.1 or 2.2 shall be taken
-     into account in determining the amount or value of any payment or
-     license.
-
-     8.4.  In the event of termination under Sections 8.1 or 8.2 above,
-     all end user license agreements (excluding distributors and resellers)
-     which have been validly granted by You or any distributor hereunder
-     prior to termination shall survive termination.
-
-9. LIMITATION OF LIABILITY.
-
-     UNDER NO CIRCUMSTANCES AND UNDER NO LEGAL THEORY, WHETHER TORT
-     (INCLUDING NEGLIGENCE), CONTRACT, OR OTHERWISE, SHALL YOU, THE INITIAL
-     DEVELOPER, ANY OTHER CONTRIBUTOR, OR ANY DISTRIBUTOR OF COVERED CODE,
-     OR ANY SUPPLIER OF ANY OF SUCH PARTIES, BE LIABLE TO ANY PERSON FOR
-     ANY INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES OF ANY
-     CHARACTER INCLUDING, WITHOUT LIMITATION, DAMAGES FOR LOSS OF GOODWILL,
-     WORK STOPPAGE, COMPUTER FAILURE OR MALFUNCTION, OR ANY AND ALL OTHER
-     COMMERCIAL DAMAGES OR LOSSES, EVEN IF SUCH PARTY SHALL HAVE BEEN
-     INFORMED OF THE POSSIBILITY OF SUCH DAMAGES. THIS LIMITATION OF
-     LIABILITY SHALL NOT APPLY TO LIABILITY FOR DEATH OR PERSONAL INJURY
-     RESULTING FROM SUCH PARTY'S NEGLIGENCE TO THE EXTENT APPLICABLE LAW
-     PROHIBITS SUCH LIMITATION. SOME JURISDICTIONS DO NOT ALLOW THE
-     EXCLUSION OR LIMITATION OF INCIDENTAL OR CONSEQUENTIAL DAMAGES, SO
-     THIS EXCLUSION AND LIMITATION MAY NOT APPLY TO YOU.
-
-10. U.S. GOVERNMENT END USERS.
-
-     The Covered Code is a "commercial item," as that term is defined in
-     48 C.F.R. 2.101 (Oct. 1995), consisting of "commercial computer
-     software" and "commercial computer software documentation," as such
-     terms are used in 48 C.F.R. 12.212 (Sept. 1995). Consistent with 48
-     C.F.R. 12.212 and 48 C.F.R. 227.7202-1 through 227.7202-4 (June 1995),
-     all U.S. Government End Users acquire Covered Code with only those
-     rights set forth herein.
-
-11. MISCELLANEOUS.
-
-     This License represents the complete agreement concerning subject
-     matter hereof. If any provision of this License is held to be
-     unenforceable, such provision shall be reformed only to the extent
-     necessary to make it enforceable. This License shall be governed by
-     California law provisions (except to the extent applicable law, if
-     any, provides otherwise), excluding its conflict-of-law provisions.
-     With respect to disputes in which at least one party is a citizen of,
-     or an entity chartered or registered to do business in the United
-     States of America, any litigation relating to this License shall be
-     subject to the jurisdiction of the Federal Courts of the Northern
-     District of California, with venue lying in Santa Clara County,
-     California, with the losing party responsible for costs, including
-     without limitation, court costs and reasonable attorneys' fees and
-     expenses. The application of the United Nations Convention on
-     Contracts for the International Sale of Goods is expressly excluded.
-     Any law or regulation which provides that the language of a contract
-     shall be construed against the drafter shall not apply to this
-     License.
-
-12. RESPONSIBILITY FOR CLAIMS.
-
-     As between Initial Developer and the Contributors, each party is
-     responsible for claims and damages arising, directly or indirectly,
-     out of its utilization of rights under this License and You agree to
-     work with Initial Developer and Contributors to distribute such
-     responsibility on an equitable basis. Nothing herein is intended or
-     shall be deemed to constitute any admission of liability.
-
-13. MULTIPLE-LICENSED CODE.
-
-     Initial Developer may designate portions of the Covered Code as
-     "Multiple-Licensed".  "Multiple-Licensed" means that the Initial
-     Developer permits you to utilize portions of the Covered Code under
-     Your choice of the NPL or the alternative licenses, if any, specified
-     by the Initial Developer in the file described in Exhibit A.
-
-EXHIBIT A -Mozilla Public License.
-
-     ``The contents of this file are subject to the Mozilla Public License
-     Version 1.1 (the "License"); you may not use this file except in
-     compliance with the License. You may obtain a copy of the License at
-     http://www.mozilla.org/MPL/
-
-     Software distributed under the License is distributed on an "AS IS"
-     basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
-     License for the specific language governing rights and limitations
-     under the License.
-
-     The Original Code is ______________________________________.
-
-     The Initial Developer of the Original Code is ________________________.
-     Portions created by ______________________ are Copyright (C) ______
-     _______________________. All Rights Reserved.
-
-     Contributor(s): ______________________________________.
-
-     Alternatively, the contents of this file may be used under the terms
-     of the _____ license (the  "[___] License"), in which case the
-     provisions of [______] License are applicable instead of those
-     above.  If you wish to allow use of your version of this file only
-     under the terms of the [____] License and not to allow others to use
-     your version of this file under the MPL, indicate your decision by
-     deleting  the provisions above and replace  them with the notice and
-     other provisions required by the [___] License.  If you do not delete
-     the provisions above, a recipient may use your version of this file
-     under either the MPL or the [___] License."
-
-     [NOTE: The text of this Exhibit A may differ slightly from the text of
-     the notices in the Source Code files of the Original Code. You should
-     use the text of this Exhibit A rather than the text found in the
-     Original Code Source Code for Your Modifications.]
-
diff --git a/mcs/LICENSE.MSPL b/mcs/LICENSE.MSPL
deleted file mode 100644 (file)
index 79629b2..0000000
+++ /dev/null
@@ -1,27 +0,0 @@
-Microsoft Permissive License (Ms-PL)\r
\r
-       This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software.\r
\r
-1. Definitions\r
-\r
-       The terms \93reproduce,\94 \93reproduction,\94 \93derivative works,\94 and \93distribution\94 have the same meaning here as under U.S. copyright law.\r
-       A \93contribution\94 is the original software, or any additions or changes to the software.\r
-       A \93contributor\94 is any person that distributes its contribution under this license.\r
-        \93Licensed patents\94 are a contributor\92s patent claims that read directly on its contribution.\r
\r
-2. Grant of Rights\r
-\r
-       (A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free copyright license to reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution or any derivative works that you create.\r
-       (B) Patent Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free license under its licensed patents to make, have made, use, sell, offer for sale, import, and/or otherwise dispose of its contribution in the software or derivative works of the contribution in the software.\r
\r
-3. Conditions and Limitations\r
-\r
-       (A) No Trademark License- This license does not grant you rights to use any contributors\92 name, logo, or trademarks.\r
-       (B) If you bring a patent claim against any contributor over patents that you claim are infringed by the software, your patent license from such contributor to the software ends automatically.\r
-       (C) If you distribute any portion of the software, you must retain all copyright, patent, trademark, and attribution notices that are present in the software.\r
-       (D) If you distribute any portion of the software in source code form, you may do so only under this license by including a complete copy of this license with your distribution. If you distribute any portion of the software in compiled or object code form, you may only do so under a license that complies with this license.\r
-       (E) The software is licensed \93as-is.\94 You bear the risk of using it. The contributors give no express warranties, guarantees or conditions. You may have additional consumer rights under your local laws which this license cannot change. To the extent permitted under your local laws, the contributors exclude the implied warranties of merchantability, fitness for a particular purpose and non-infringement.\r
-       (F) If you distribute the software or derivative works with programs you develop, you agree to indemnify, defend, and hold harmless all contributors from any claims, including attorneys\92 fees, related to the distribution or use of your programs.  For clarity, you have no such obligations to a contributor for any claims based solely on the unmodified contributions of that contributor.\r
-       (G) If you make any additions or changes to the original software, you may only distribute them under a new namespace.  In addition, you will clearly identify your changes or additions as your own.\r
-\r
-\r
diff --git a/mcs/MIT.X11 b/mcs/MIT.X11
deleted file mode 100644 (file)
index cb4a84d..0000000
+++ /dev/null
@@ -1,21 +0,0 @@
-Copyright (c) 2001, 2002, 2003 Ximian, Inc and the individuals listed
-on the ChangeLog entries.
-
-Permission is hereby granted, free of charge, to any person obtaining
-a copy of this software and associated documentation files (the
-"Software"), to deal in the Software without restriction, including
-without limitation the rights to use, copy, modify, merge, publish,
-distribute, sublicense, and/or sell copies of the Software, and to
-permit persons to whom the Software is furnished to do so, subject to
-the following conditions:
-
-The above copyright notice and this permission notice shall be
-included in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
index e31193319f10b19b532b58db560ea1bfce425177..7dbfb638917892d2637276347599b56aa8b8cfba 100644 (file)
@@ -86,15 +86,9 @@ package := mcs-$(VERSION)
 DISTFILES = \
        AUTHORS                 \
        COPYING                 \
-       COPYING.LIB             \
        INSTALL.txt             \
-       LICENSE                 \
-       LICENSE.GPL             \
-       LICENSE.LGPL            \
-       LICENSE.MPL             \
        Makefile                \
        mkinstalldirs           \
-       MIT.X11                 \
        MonoIcon.png            \
        README                  \
        ScalableMonoIcon.svg    \
index 2a64e0f6ef65989c43185a511fdc9bf9e6b74332..f23a12d69bfe078c688a21ac954522a7a7fe3ece 100644 (file)
@@ -85,46 +85,3 @@ If you want to only run the tests in a single fixture (say
 Thanks a lot to Sergey Chaban for his help during the development of
 the C# compiler.
 
-* LICENSE
-=========
-
-The mcs C# compiler and monoresgen are licensed to you under the GPL, version 2.
-The complete text of the GPL is in the 'COPYING' file.
-
-    Copyright (C) 2001-2002  Ximian, Inc.
-
-    This program is free software; you can redistribute it and/or modify
-    it under the terms of version 2 of the GNU General Public License as 
-    published by the Free Software Foundation.
-
-    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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
-
-The class libraries are licensed according to the following license:
-
-    Copyright (C) 2001-2002  Ximian, Inc.
-
-Permission is hereby granted, free of charge, to any person obtaining a
-copy of this software and associated documentation files (the "Software"),
-to deal in the Software without restriction, including without limitation
-the rights to use, copy, modify, merge, publish, distribute, sublicense,
-and/or sell copies of the Software, and to permit persons to whom the
-Software is furnished to do so, subject to the following conditions:
-
-The above copyright notice and this permission notice shall be included
-in all copies or substantial portions of the Software.
-
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
-THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
-OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
-ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
-OTHER DEALINGS IN THE SOFTWARE.
-
index 8048c5fdf3beb54fe2bdcdd761616bf177795d5b..f33fcccf2d7635f498496404d5ed0dbadd8f1d56 100644 (file)
@@ -28,7 +28,8 @@ COMMON_SRCS = \
        Locale.cs                       \
        MonoTODOAttribute.cs \
        basic-profile-check.cs          \
-       SR.cs
+       SR.cs   \
+       AssemblyRef.cs
 
 DISTFILES = \
        README.makefiles                \
index 658faa991ce56d6801dce5537d582c4f64333bab..145665799ccaaccd74e1c7a9617f8f1d725da98b 100644 (file)
@@ -10,7 +10,7 @@
 CODEPAGE = 65001
 
 RUNTIME_FLAGS = 
-TEST_HARNESS = $(topdir)/class/lib/$(PROFILE)/nunit-console.exe
+TEST_HARNESS = $(topdir)/class/lib/$(PROFILE)/$(PARENT_PROFILE)nunit-console.exe
 MCS_FLAGS = 
 MBAS_FLAGS = $(PLATFORM_DEBUG_FLAGS)
 LIBRARY_FLAGS = /noconfig
index 7ac3b33846239297cc064116a273e3035c542d00..29ba89909e6d397d8d2012a09999717af7561526 100644 (file)
@@ -31,6 +31,9 @@ ifdef base_prog_config
 PROGRAM_config := $(build_libdir)$(PROGRAM).config
 endif
 
+sn = $(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)/sn.exe
+SN = MONO_PATH="$(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)$(PLATFORM_PATH_SEPARATOR)$$MONO_PATH" $(RUNTIME) $(RUNTIME_FLAGS) $(sn) -q
+
 the_lib = $(the_libdir)$(base_prog)
 build_lib = $(build_libdir)$(base_prog)
 
@@ -110,7 +113,10 @@ endif
 $(the_lib): $(the_libdir)/.stamp
 
 $(build_lib): $(BUILT_SOURCES) $(EXTRA_SOURCES) $(response) $(build_libdir:=/.stamp)
-       $(PROGRAM_COMPILE) -target:exe -out:$@ $(BUILT_SOURCES) $(EXTRA_SOURCES) @$(response)
+       $(PROGRAM_COMPILE) $(MCS_REFERENCES) -target:exe -out:$@ $(BUILT_SOURCES) $(EXTRA_SOURCES) @$(response)
+ifdef PROGRAM_SNK
+       $(Q) $(SN) -R $@ $(PROGRAM_SNK)
+endif
 
 ifdef PROGRAM_USE_INTERMEDIATE_FILE
 $(the_lib): $(build_lib)
@@ -143,6 +149,9 @@ endif
 
 -include $(makefrag)
 
+MCS_REFERENCES = $(patsubst %,-r:$(topdir)/class/lib/$(PROFILE)/%.dll,$(LIB_REFS))
+MCS_REFERENCES += $(patsubst %,-r:$(topdir)/class/lib/$(PROFILE)/%.exe,$(EXE_REFS))
+
 all-local: $(makefrag) $(extra_targets)
 
 csproj-local:
index 2eb4995bdd80c6569867178350c70fdaad71a2b6..14a0a01db59d07b4503b9a5d1ae8882e25442524 100644 (file)
@@ -43,7 +43,7 @@ sort -u $outfile.inc > $outfile.inc_s
 rm -f $outfile.inc
 
 
-if test -n "$excfile"; then
+if test -n "$excfile" -a -f "$excfile"; then
     process_includes $excfile $outfile.exc
 fi
 
index 1df98aeea1f035eb5e187138f58761eaccab60be..895d67b6933b4e14cff75d8b31433a4323a8c197 100644 (file)
 # Have to rename to handle differences between assembly/directory names
 DEP_LIBS=$(patsubst System.Xml,System.XML,$(LIB_REFS))
 
-LIB_MCS_FLAGS += $(patsubst %,-r:%.dll,$(LIB_REFS))
+_FILTER_OUT = $(foreach x,$(2),$(if $(findstring $(1),$(x)),,$(x)))
+
+LIB_REFS_FULL = $(call _FILTER_OUT,=, $(LIB_REFS))
+LIB_REFS_ALIAS = $(filter-out $(LIB_REFS_FULL),$(LIB_REFS))
+
+LIB_MCS_FLAGS += $(patsubst %,-r:$(topdir)/class/lib/$(PROFILE)/%.dll,$(LIB_REFS_FULL))
+LIB_MCS_FLAGS += $(patsubst %,-r:%.dll, $(subst =,=$(topdir)/class/lib/$(PROFILE)/,$(LIB_REFS_ALIAS)))
 
 sourcefile = $(LIBRARY).sources
 
@@ -29,24 +35,11 @@ PROFILE_excludes = $(wildcard $(PROFILE)_$(LIBRARY).exclude.sources)
 sourcefile = $(depsdir)/$(PROFILE)_$(LIBRARY).sources
 library_CLEAN_FILES += $(sourcefile)
 
-ifdef EXTENSION_MODULE
-EXTENSION_include = $(wildcard $(topdir)/../../mono-extensions/mcs/$(thisdir)/$(PROFILE)_$(LIBRARY).sources)
-else
-EXTENSION_include = $(wildcard $(PROFILE)_opt_$(LIBRARY).sources)
-endif
-
-
-ifdef EXTENSION_MODULE
-EXTENSION_exclude = $(wildcard $(topdir)/../../mono-extensions/mcs/$(thisdir)/$(PROFILE)_$(LIBRARY).exclude.sources)
-else
-EXTENSION_exclude = $(wildcard $(PROFILE)_opt_$(LIBRARY).exclude.sources)
-endif
-
 # Note, gensources.sh can create a $(sourcefile).makefrag if it sees any '#include's
 # We don't include it in the dependencies since it isn't always created
-$(sourcefile): $(PROFILE_sources) $(PROFILE_excludes) $(topdir)/build/gensources.sh $(EXTENSION_include)
+$(sourcefile): $(PROFILE_sources) $(PROFILE_excludes) $(topdir)/build/gensources.sh
        @echo Creating the per profile list $@ ...
-       $(SHELL) $(topdir)/build/gensources.sh $@ '$(PROFILE_sources)' '$(PROFILE_excludes)' '$(EXTENSION_include)' '$(EXTENSION_exclude)'
+       $(SHELL) $(topdir)/build/gensources.sh $@ '$(PROFILE_sources)' '$(PROFILE_excludes)'
 endif
 
 PLATFORM_excludes := $(wildcard $(LIBRARY).$(PLATFORM)-excludes)
@@ -253,6 +246,7 @@ dist-local: dist-default
        for f in `$(topdir)/tools/removecomments.sh $(wildcard *$(LIBRARY).sources)` $(TEST_FILES) ; do \
          case $$f in \
          ../*) : ;; \
+         *.g.cs) : ;; \
          *) dest=`dirname "$$f"` ; \
             case $$subs in *" $$dest "*) : ;; *) subs=" $$dest$$subs" ; $(MKINSTALLDIRS) $(distdir)/$$dest ;; esac ; \
             cp -p "$$f" $(distdir)/$$dest || exit 1 ;; \
index 5273928a0ed6143d4fff29ee27776f826f67a3f0..3b4c7e0706e4fb4862fc5eaf17fffb0d805e6c65 100644 (file)
@@ -12,8 +12,8 @@ MCS = MONO_PATH="$(topdir)/class/lib/$(BOOTSTRAP_PROFILE)$(PLATFORM_PATH_SEPARAT
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
-PROFILE_MCS_FLAGS = -d:NET_4_0 -d:NET_4_5 -d:MONO -d:DISABLE_CAS_USE -nowarn:1699 -nostdlib -lib:$(topdir)/class/lib/$(PROFILE) $(DEFAULT_REFERENCES)
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
+PROFILE_MCS_FLAGS = -d:NET_4_0 -d:NET_4_5 -d:MONO -d:DISABLE_CAS_USE -nowarn:1699 -nostdlib $(DEFAULT_REFERENCES)
 
 NO_SIGN_ASSEMBLY = yes
 NO_TEST = yes
index 6f6108c08aa7d89ab89dda7de1b0247e3449494c..70908afa4e194fa55f910c259b89c231f11eebfd 100644 (file)
@@ -11,7 +11,7 @@ RESGEN = resgen2
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
 
 PROFILE_MCS_FLAGS = \
        -d:NET_1_1 \
@@ -26,7 +26,6 @@ PROFILE_MCS_FLAGS = \
        -d:DISABLE_CAS_USE \
        -nowarn:1699 \
        -nostdlib \
-       -lib:$(topdir)/class/lib/$(PROFILE) \
        $(DEFAULT_REFERENCES) \
        $(PLATFORM_DEBUG_FLAGS)
 
index 0c3c8125cfdcda56f5d59100d2dacb825666386b..f13e65d83ccb7bdfadde12ab9a255ee7001898aa 100644 (file)
@@ -11,7 +11,7 @@ RESGEN = resgen2
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
 
 PROFILE_MCS_FLAGS = \
        -d:NET_1_1 \
@@ -28,7 +28,6 @@ PROFILE_MCS_FLAGS = \
        -d:DISABLE_COM \
        -nowarn:1699 \
        -nostdlib \
-       -lib:$(topdir)/class/lib/$(PROFILE) \
        $(DEFAULT_REFERENCES) \
        $(PLATFORM_DEBUG_FLAGS)
 
index 49f85dcf8ee26c7273e367ef1a94366295cb9f47..9ea27d6c9c7f866de0d850093cad9056a9301ab9 100644 (file)
@@ -11,7 +11,7 @@ RESGEN = resgen2
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
 
 PROFILE_MCS_FLAGS = \
        -d:NET_1_1 \
@@ -28,7 +28,6 @@ PROFILE_MCS_FLAGS = \
        -d:ANDROID \
        -nowarn:1699 \
        -nostdlib \
-       -lib:$(topdir)/class/lib/$(PROFILE) \
        $(DEFAULT_REFERENCES) \
        $(PLATFORM_DEBUG_FLAGS)
 
index 7e963cb73c0e257ef02707a6f868c3259f9bd882..f127fd7d19043fc3f7a79656697477b03a109cfa 100644 (file)
@@ -13,7 +13,7 @@ RESGEN := $(dir $(shell which $(EXTERNAL_MCS)))resgen2
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
 PROFILE_MCS_FLAGS = \
        -d:NET_1_1 \
        -d:NET_2_0 \
@@ -30,7 +30,6 @@ PROFILE_MCS_FLAGS = \
        -d:FEATURE_INTERCEPTABLE_THREADPOOL_CALLBACK \
        -nowarn:1699 \
        -nostdlib \
-       -lib:$(topdir)/class/lib/$(PROFILE) \
        $(DEFAULT_REFERENCES) \
        $(PLATFORM_DEBUG_FLAGS)
 
index a634dac392874f47f2629511bd5195a631403a69..a93b03b7f6b4fffa902356cac8ca5e2728aa2400 100644 (file)
@@ -10,8 +10,8 @@ MCS = MONO_PATH="$(topdir)/class/lib/$(BOOTSTRAP_PROFILE)$(PLATFORM_PATH_SEPARAT
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
-PROFILE_MCS_FLAGS = -d:NET_4_0 -d:NET_4_5 -d:NET_4_6 -d:MONO -d:DISABLE_CAS_USE  -nowarn:1699 -nostdlib -lib:$(topdir)/class/lib/$(PROFILE) $(DEFAULT_REFERENCES) $(PLATFORM_DEBUG_FLAGS)
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
+PROFILE_MCS_FLAGS = -d:NET_4_0 -d:NET_4_5 -d:NET_4_6 -d:MONO -d:DISABLE_CAS_USE  -nowarn:1699 -nostdlib $(DEFAULT_REFERENCES) $(PLATFORM_DEBUG_FLAGS)
 
 FRAMEWORK_VERSION = 4.5
 XBUILD_VERSION = 4.0
index a9a6ef9ab25b2d2eb070270665be2120624311e5..d3cbdb5d972e886f246edaf9ffef7269086697e5 100644 (file)
@@ -9,7 +9,7 @@ RESGEN := $(dir $(shell which $(EXTERNAL_MCS)))resgen2
 profile-check:
        @:
 
-DEFAULT_REFERENCES = -r:mscorlib.dll
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll
 
 PROFILE_MCS_FLAGS = \
        -d:NET_1_1 \
@@ -27,7 +27,6 @@ PROFILE_MCS_FLAGS = \
        -d:XAMARIN_MODERN \
        -nowarn:1699 \
        -nostdlib \
-       -lib:$(topdir)/class/lib/$(PROFILE) \
        $(DEFAULT_REFERENCES) \
        $(PLATFORM_DEBUG_FLAGS)
 
index 7150d2529e9085cf0967696a6d2cd8855916af8f..a0b681071ddb49c38d4c62d9ed349c669e4391d8 100644 (file)
@@ -2,6 +2,10 @@
 
 include $(topdir)/build/profiles/net_4_x.make
 
-PROFILE_MCS_FLAGS := $(PROFILE_MCS_FLAGS) -d:XBUILD_12 -d:MONO -d:DISABLE_CAS_USE  -lib:$(topdir)/class/lib/net_4_x
+PARENT_PROFILE = ../net_4_x/
+DEFAULT_REFERENCES = -r:$(topdir)/class/lib/net_4_x/mscorlib.dll
+PROFILE_MCS_FLAGS := $(PROFILE_MCS_FLAGS) -d:XBUILD_12
+
+RESGEN_EXE = $(topdir)/class/lib/net_4_x/resgen.exe
 
 XBUILD_VERSION = 12.0
index 4e35ffc2305ef7a8c198773b45bdfda9b53b012a..60809393a62f1c526c67bd61f29d471753926fa9 100644 (file)
@@ -1,7 +1,7 @@
 # -*- makefile -*-
 
-include $(topdir)/build/profiles/net_4_x.make
+include $(topdir)/build/profiles/xbuild_12.make
 
-PROFILE_MCS_FLAGS := $(PROFILE_MCS_FLAGS) -d:XBUILD_12 -d:XBUILD_14 -d:MONO -d:DISABLE_CAS_USE  -lib:$(topdir)/class/lib/net_4_x
+PROFILE_MCS_FLAGS := $(PROFILE_MCS_FLAGS) -d:XBUILD_14
 
 XBUILD_VERSION = 14.0
index 54c946a8730f775da8f7976bdcec8fba17a3edf3..5fda8826d12968f30542b58a29219ceff5d11208 100644 (file)
@@ -43,9 +43,10 @@ MKINSTALLDIRS = $(SHELL) $(topdir)/mkinstalldirs
 INTERNAL_MBAS = $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/mbas/mbas.exe
 INTERNAL_GMCS = $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)/mcs.exe
 INTERNAL_ILASM = $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/class/lib/$(PROFILE)/ilasm.exe
-corlib = mscorlib.dll
+INTERNAL_CSC = $(RUNTIME) $(RUNTIME_FLAGS) $(CSC_LOCATION)
 
-INTERNAL_RESGEN = $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/class/lib/$(PROFILE)/resgen.exe
+RESGEN_EXE = $(topdir)/class/lib/$(PROFILE)/resgen.exe
+INTERNAL_RESGEN = $(RUNTIME) $(RUNTIME_FLAGS) $(RESGEN_EXE)
 RESGEN = MONO_PATH="$(topdir)/class/lib/$(PROFILE)$(PLATFORM_PATH_SEPARATOR)$$MONO_PATH" $(INTERNAL_RESGEN)
 STRING_REPLACER = MONO_PATH="$(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)$(PLATFORM_PATH_SEPARATOR)$$MONO_PATH" $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)/cil-stringreplacer.exe
 
index e8d52d00332ba0d9a181e513ee90c06fd297b6e0..7f27dd9fd511c66eca5e9044e336c75bc5157a27 100644 (file)
@@ -25,7 +25,9 @@ else
 test_nunit_lib = nunit.framework.dll nunit.core.dll nunit.util.dll nunit.mocks.dll
 endif
 
-test_nunit_dep = $(test_nunit_lib:%=$(topdir)/class/lib/$(PROFILE)/%)
+TEST_LIB_MCS_FLAGS = $(patsubst %,-r:$(topdir)/class/lib/$(PROFILE)/%.dll,$(TEST_LIB_REFS))
+
+test_nunit_dep = $(test_nunit_lib:%=$(topdir)/class/lib/$(PROFILE)/$(PARENT_PROFILE)%)
 test_nunit_ref = $(test_nunit_dep:%=-r:%)
 tests_CLEAN_FILES += TestResult*.xml
 
@@ -41,7 +43,7 @@ test_sourcefile_excludes = $(test_lib).excludes
 test_pdb = $(test_lib:.dll=.pdb)
 test_response = $(depsdir)/$(test_lib).response
 test_makefrag = $(depsdir)/$(test_lib).makefrag
-test_flags = -r:$(the_assembly) $(test_nunit_ref) $(TEST_MCS_FLAGS)
+test_flags = -r:$(the_assembly) $(test_nunit_ref) $(TEST_MCS_FLAGS) $(TEST_LIB_MCS_FLAGS)
 tests_CLEAN_FILES += $(ASSEMBLY:$(ASSEMBLY_EXT)=_test*.dll) $(ASSEMBLY:$(ASSEMBLY_EXT)=_test*.pdb) $(test_response) $(test_makefrag)
 
 ifndef HAVE_CS_TESTS
@@ -58,11 +60,15 @@ $(test_nunit_dep): $(topdir)/build/deps/nunit-$(PROFILE).stamp
 
 ifdef NUNIT_LITE
 $(topdir)/build/deps/nunit-$(PROFILE).stamp:
+ifndef PARENT_PROFILE
        cd ${topdir}/tools/nunit-lite && $(MAKE)
+endif
        echo "stamp" >$@
 else
 $(topdir)/build/deps/nunit-$(PROFILE).stamp:
+ifndef PARENT_PROFILE
        cd ${topdir}/nunit24 && $(MAKE)
+endif
        echo "stamp" >$@
 endif
 
index 907ce82bb5bbd804a374c994167c2474a3479ec8..8700935681bd7b9038775d2d58304eb83be90ec2 100644 (file)
@@ -3,7 +3,7 @@ SUBDIRS =
 include ../../build/rules.make
 
 LIBRARY = Accessibility.dll
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index 1bc0fd2f2773f1c6f2c6e9a93d5de3ffddff8845..d63e7af0565267712121ff183e65084bf9ef92b0 100644 (file)
@@ -8,7 +8,7 @@ OTHER_RES = $(RESOURCE_FILES)
 
 LIBRARY = Commons.Xml.Relaxng.dll
 LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = /r:$(corlib) \
+LIB_MCS_FLAGS = \
        $(foreach r, $(OTHER_RES), /resource:$(r),$(notdir $(r)))
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 EXTRA_DISTFILES = \
index 9c11dbac65c299d9b2f5ad86cbe5b77fa28b999d..74debbe57e66c8e91a2587a24e111aa2b826f924 100644 (file)
@@ -8,7 +8,7 @@ LIBRARY_COMPAT = yes
 LIBRARY_SNK = SharpZipLib.key
 
 LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = -r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 EXTRA_DISTFILES = SharpZipLib.pub $(LIBRARY_SNK)
 
index 3afddcca8fa2e31a225144ff1f86066acfa865f2..54ff581cee0b50832f0065c1d6f68a8cfd840820 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Cscompmgd.dll
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 LIBRARY_NAME = cscompmgd.dll
 
index 0e432dc33b19daa4ce376521876b7c89027df2e0..366921c583ffa6a658be493402581d2ac40a06c7 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = CustomMarshalers.dll
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index 12f045eebd8ec6253a500ab92c300e7c4c54f975..d984f22ecd51922003ddc2fb5dd3a7bf711c4f0d 100644 (file)
@@ -37,7 +37,9 @@ doc-update-local:
 doc-update-recursive:
        @echo "do not recurse the Facades folder"
 
-System System.Core System.ComponentModel.DataAnnotations System.Numerics System.Runtime.Serialization System.XML System.ComponentModel.Composition System.ServiceModel System.Xml.Linq:
+System System.Core System.ComponentModel.DataAnnotations System.Numerics System.Runtime.Serialization System.XML \
+System.ComponentModel.Composition System.ServiceModel System.Xml.Linq System.Data System.IO.Compression.FileSystem \
+System.ServiceProcess System.Security System.Net.Http.WebRequest System.Net.Http:
 
 all-local-aot:
 
index 4b0a8ce48f852315136014265fd5026e902eee2b..d1b93730000cfeb9d7a940589a9551dd045769e6 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = Microsoft.Win32.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 68c77b28ef9b7ab8da342c4ffc948e0cef4b36ed..0b5f4acf6daad43a1597f99ada62b9ebd4f05fc2 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = Microsoft.Win32.Registry.AccessControl.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 95a931f2a73e6c76d6e18cb230bab4b083e8f8eb..5f1030b7c72c610cf09e6c850a32935ca7874590 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = Microsoft.Win32.Registry.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index a428634b310354eea16aa4b1464e33d3906562a4..9170d927e04e6a6100557b4bd0eabadc421dd750 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.AppContext.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 9fe40d3d849ba6f5fe9a1b854d89d270fb47f01b..d94e5d55dd2aa4ad2de702786f5ad8e7835bec6e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Collections.Concurrent.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 6aa88932bd39bd51fdb5b480a0fc15c6c4844e00..f2f3cdb4772de684efb7216f3b876b12a3abb2f9 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Collections.NonGeneric.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 7730dc6182e9ce19d9066541087e11619c71a1b6..d391fa9ac5190ed4715718989e3ae3d0b0213ef3 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Collections.Specialized.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e91fa63b8d8946bd8b7d8bfc58b8f9039ffb6a97..dc6dca0073a2334fa85a0aa17e1017c539d8d556 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Collections.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 0e5a336b82cfd49d13d88ef67dbf30ca33847a0d..a4f1cc41c4d0305260e88acd5defefb4817be0e9 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ComponentModel.Annotations.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ComponentModel.DataAnnotations
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 3bb78c169959296cd387ae7f09351add9b11ded6..48a6b9c11e617451abde35a362f117b433457a89 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ComponentModel.EventBasedAsync.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 8b46af0e4c20bec7dd4b688c8be54e40dbddd4ad..dac065757dee333e4ff0d549b12c6223ac8c1f2d 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ComponentModel.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 9479c31e5d55ff566a80649825d80416fac742f4..6062e304a95bddb5401c33402610baa81e6b1251 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ComponentModel.TypeConverter.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 57c23bab8fcb480ec9199e685f7a0297d96e7cde..33b88f9541ee8bbac2b728a5064e1a6ef3dd7e33 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ComponentModel.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 7ec5ccd75e51a9b9b5fb3357bd4fd3ff911aa004..ea7312a4d7060b96f47c03c998097150cc34720f 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Console.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index ca5b55bb5e4dfbdb31f8bb7e204654ee536e14ab..30bf3dd018146c2ca81002fde79578ff7f6457c1 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Data.Common.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Data.dll
+LIB_REFS = System System.Data
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 0fa130c8e282d2a27762cf34c4acf6278a628f29..f5eb7097fd6366eaad0662aa3f5f809e40fe6874 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Data.SqlClient.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Data.dll /r:System.Xml.dll
+LIB_REFS = System System.Data System.Xml
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 23dad544fc916db57359e244df2f82a805919bd4..391da57605b41150b50ce48906995e07bea39df2 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Diagnostics.Contracts.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 34574abc438294f2009aacc169f0ee69ab33a4df..0eccd8767190f9b3a811a712cf0522f6e3a4cef2 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.Debug.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 2d2c4bfe8bbb783b2159ba9e254bd68a055e9bf3..1ac2f6cc2a05917d5e5d678a5a348715a75496b2 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.FileVersionInfo.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 499d313fc6cdc2b3b2974083d721641cbd401735..beda86068884cf88af0a51a363dd73dcca126150 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.PerformanceCounter.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index c6980725fd1d3b9b2a3bac340130b476134c2cb3..83fd768e25124252caa659b24c03af6afdc7f86c 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.Process.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 169d8b79e1e61e7fd1a9ac44b712d11c37d90d7b..25d8ac37eddd1351ee41e37670615d9b8df46531 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.StackTrace.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 27e24e5ed7a223b4bd997a432b0d26d4ee02e314..aa7c6dc119fc4cfa8f0d8ed154b0cfcb4fa4ec9e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.TextWriterTraceListener.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 494f8b90da060b4dbce7f760c85e0b015540994b..3d9b5158255726324e164ef659a6f48d05f977bd 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.Tools.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index a109b64df9ac0b9102519fab385426eb04e91a1f..342e82dbf4a4288cc8cfa0269205ba1aa6b77de7 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.TraceEvent.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 2dbd5475cca82641a0af997389e9b86bc0582941..3467273f7c9ea984a9a7770ce90dc0e44359ee36 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Diagnostics.TraceSource.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 53a49cfff704df5cbefb9b134f291956caffa328..14b380da866454c7569c53a115dfa4e473422415 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Diagnostics.Tracing.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 9380c0ecba4f95c19ba8b621b03f7c82d5dcf9af..a6bcda9f3deddfa3d64379e1b6908a4d1e884fe3 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Dynamic.Runtime.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1659260c032b06ce4d0fb36e2e12558812ab73a9..5f419e9b635d47e2424ac026cdc42178f821cc79 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Globalization.Calendars.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e4923237e7b79385a76d073e0722c9a5a461419d..d3a57fa307dbd8b7121b25630aa667270b3dc640 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Globalization.Extensions.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e94f4b5561bbe4b68878cc75eca0e2ef3d851661..4f01dfeb76258fc89d9d03cecedd4742bf77d306 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Globalization.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 0865314a1bda3abaed6ff8033176b11a9859d7f1..b4e4896a6295a8936564f4a0539974952652070c 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.IO.Compression.ZipFile.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.IO.Compression.FileSystem.dll
+LIB_REFS = System System.IO.Compression.FileSystem
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 6574fc6249952d0b4ddb143a5c2bcc03cf632b59..0198747a8a312def61d8cb153e45a6b6d038c168 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.FileSystem.AccessControl.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 096d6c7a7facd196627c335924caea1de7d4cfa3..0925c49d1557f854176a41a134cbcd81ad6bf124 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.FileSystem.DriveInfo.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 2622a088f2d2547165a9965bef8781de3e51bc12..31b27077e454a42cb23a1d7436d72e0498c6334b 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.FileSystem.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 2a4d25e107348b40b171c36f5d4da5414f7a5fd0..caade8a02a0195d34405de7b8659995ef95b0d31 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.FileSystem.Watcher.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index cbd49ccc53525461d170e49f2cc040e30a8264f1..178aa60efeaaad5830ac94aaab910a13751441e2 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.FileSystem.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e89d4be370bff6b7b2db7177c7470edc9ab28814..be6a315004b208b1c49e37455206199af6e43093 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.IsolatedStorage.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1ea56e44d9432db6cd5104cca5ca05b32611ba71..656b03cd1262185c1b50734329bc9296795d8515 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.IO.MemoryMappedFiles.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Core.dll
+LIB_REFS = System System.Core
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 999b161afd3c7fdcc284a39e5cbe958651a3b734..0d156aafeb131b3bf55145cd637bb68770340e39 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.IO.Pipes.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Core.dll
+LIB_REFS = System System.Core
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index c65888b23119152c3780cb424380e97c5bd4779c..c1605d9ccf85284ae1fa300fbc17dc35dfb10eb9 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.UnmanagedMemoryStream.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 42a6a9413b47bdab5bbf0052fc480259c8a19e99..89fc0db09634da4466bd382a6874697d517e21ab 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.IO.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index d2ad276ef09b821064fa829c6c23ecc933c16c01..bb78580fb433de302a0fdf8ef84e8abe7532799e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Linq.Expressions.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index d68ebb41633709974ae71f366d6b7735bdbef05b..7d314bf5e9502836ca18c6ec152739898fba656c 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Linq.Parallel.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1f0225e3aeab978987d912eedf0b8ade5b17a445..6ea4c746ec840f02659775c5a1d330f33bb6c516 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Linq.Queryable.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 17bcabbdf83bb028dc8fd82f28cebeb0c9d0dbd3..d9778697d4c882d682b44b80d7da16b3a0136284 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Linq.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 4efed6d1b282b95efb47cbbc2d355990e87ce01e..293f80d25d36c56bcde1dd969c536cd941d29d6b 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.AuthenticationManager.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 9826235d5b1b5b01139196b8ba490e066808e91c..bbdcfce759232bb82559b6705da145b52307792a 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Cache.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 202bfbe892aba93b0356b9f9626664d9f218d49e..7750bbae45a12a74751e744aa15684e2309aac89 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Net.Http.WebRequestHandler.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Net.Http.WebRequest.dll /r:System.Net.Http.dll
+LIB_REFS = System System.Net.Http.WebRequest System.Net.Http
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 401f473303c78037d6d58df94c47046c9f5e7396..3109e7076150771cdc3703a58b00258b94b09a77 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.HttpListener.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 32aca2f9665420600d201bb2d5a9499c83e9a5dd..fe936b17d9141732b41bf59c2e95fe8096f9f23f 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Mail.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index ae8b68c79d68b08b685526fdfb1fdd796ffea20b..142a303c38e0b9869ff4e7c185efb0d3977661e0 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.NameResolution.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 29df735469a22123eafc2e9d28163f4c1fd6331f..bc2a7ec81660b1daf4d03a1da95c73f02d8202aa 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.NetworkInformation.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index babbd33274be478c719ef7b019bd31c6b5106e57..bc36271325922ee154f7268ad5ccec15fd8069a6 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 947ca929cef91ae7c3a41704f7f45eb1f8a39f06..7a8a231bc3b45ac31461994436df5075a7cc81e6 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Requests.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 4eab13bc8c870e90a8ff203be795f68f61467f90..cdd7db906c94970e9fab160103797a5d2baf446f 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Security.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index bb8e7229f721bdedb2aab7f4e0d6afe4fe5875f4..f0d095317dcaeea6f0b93505b3b726053a491f7a 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.ServicePoint.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 0cd78a8dac09f04214e7e0456b16cff94bbee806..bf60d5fef6be2147d79b9b70e5ab29430dc1f651 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Sockets.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 77d83647a6d9ffc7f567085ea2122e49ac32391c..6f1a5166b8aa215aed0bc604a0f27cd72a06a610 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.Utilities.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index b3fe02b3456caade8da72a4ef77390194ca72a8b..f6ec2a06526ec525bee6876f87f7ba7dd9055bdb 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.WebHeaderCollection.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 8489220e9602c57945b8d28077d393162d791f78..2552b0e0d5b3032027e0b89eb7bf4b6221791a6e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.WebSockets.Client.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 783ae541c93d3af0459500e74594aec89b22b86e..e9fa98fd8b48fd01450122ab9bd74fc0a98b8d1c 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Net.WebSockets.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 56ca84ae0daa2b92d814c4b658b5e131364d5320..0838b23d3cfe1e301d46448072fec98ed020cb07 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ObjectModel.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index ee55fc623754b07f78cbb5d91bfc0eb44d0247d7..7b03ca8fdb0eb1b55a0f6e5b49507b65a189e0df 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Private.CoreLib.InteropServices.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 52ce0e308ad25c830d36c54686ea57fcb720fe0c..347b171983ea6f8483fa59cb2b914782d4091029 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Private.CoreLib.Threading.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index f9c54c54b2f4031fe241980dae629348dca72f0b..6ee536f7b71437a4b774e62b45834cde0297142e 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.Emit.ILGeneration.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 70a46b888d520a0311bfccc254c7206ca5531df9..93292276ab10e15f578a62e8431405bc2153544c 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.Emit.Lightweight.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 2227a3ca80f0acea2a613d60c0ac2f76accaeb1d..798d457271e1b199a3d1ade55adb63f526df5eaa 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.Emit.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index db7f3df173d8978bbda3b8522034c160c4336455..e1799cc150e5da36dfa74d857f5b85461b302b76 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.Extensions.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 99a3a39505d2072a5501f32f5981201724999951..ee500e52ecbdc726ce75a1352b9925cd4d64e5cf 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.Primitives.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 3e4d713ac5353037aee66eab5b599de85e59c8ab..b2bb49ecfd1b431029d66f45927f36d0e712e26b 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Reflection.TypeExtensions.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 862b9333ccc43509c9fe37ab453d52f5f9742856..3061a268a236132b4ab3e97479b4cd5a6f55d090 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Reflection.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 48c56ade5a33b199bf38475aab9abbabc36908db..e2795e40f7d39338970d51e1603db8126eb12771 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Resources.ReaderWriter.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 72e539364cf89dc38ca7ac96214114c61ebe0336..15f241e4091c0ca1bbc9533964eeec76f904aa8e 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Resources.ResourceManager.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 21d3f78844e17e8b91ce7bd25c04536df3abcfed..6f7f15c612e98df05db8f54e26515c807767901c 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.CompilerServices.VisualC.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 981cb5f8233e46740c20088a087db5f600d7acdc..70fd8c9330577b0c140791d38ccf5a615110ce01 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Extensions.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 396738e44e53ccbd4cfed370816717bb0bf63158..db800c29abf056babb2ba8c8ee077d8f93a9bf94 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Handles.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index a6340fb3e76fde42cd7b3347c0ef8aa00aafccd5..1aaf02e2fc58c6d2334902e8acb610e1df459464 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Runtime.InteropServices.WindowsRuntime.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 51ef698b24c1f5b14b64230d738372e2c0fa929f..dd20654dcd3a4675f21e4d31e77ab535d64f180b 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.InteropServices.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e452fc5aca5f84d2abe6e8501d24f19502be2e4b..57867bb26a13f9894d1fe689fb82339f35a94af3 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Numerics.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Numerics
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 304059eaabb16eac768554ffa94417381e4cdba8..b5ca5ce40b28333fc7b1d16bc3772b22cdbe537c 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Serialization.Json.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Runtime.Serialization
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 648884fc9b72276c82b7103587d657d025e332f6..3a2519549fc638191e38dad30136d69222edbd3a 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Serialization.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Runtime.Serialization
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index cc0aec4a369d40f21e1c667f26bd1b7781ffb351..774289eb4de9e987c0368ce80e90d818c7b7ef7e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.Serialization.Xml.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Runtime.Serialization System.Xml
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index c59de1384080e288a20a1b5f3a5368e79129067d..e8ab4049a267a27e87f64c2f7668058c18d67e5b 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Runtime.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.ComponentModel.Composition System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 3491238f861b314949c1a6100278ec2f80c0c77c..5c6ad1c09ecffa7c0aad056d7828a93449bf3610 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.AccessControl.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 72b761e38a545cdae65eb899e1b28e82073642ab..36ff76137bace6f96b5ca5552a5439e4f57235f6 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Claims.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1beaa35e01372bf07f4670eafcc4754e474d5471..4988d34843d478cb1ac0c81001090c141349d195 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.DeriveBytes.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 5bf1ccf0ab3e4c366b2ae21f30d67d69e061b646..71d37e200e0d5a4f8c55a0f64eb805898bcb2918 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.Encoding.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index b43610b676465f01bffde31cd47e558455c90c64..0598a53f1d492c67996b709b6a8fbdf5d423152e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.Encryption.Aes.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index a2c373ac08aa6e3267ab7a26502ab4acdbbf4913..03e69f1f95ae0e0e097336d9145814392b64978c 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Security.Cryptography.Encryption.ECDiffieHellman.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Core.dll
+LIB_REFS = System System.Core
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 2bae1ac269dfca35f65fd3a3b6065d512796a146..08e99941082c8f1c4bf6531a99da34dfa9b62543 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Security.Cryptography.Encryption.ECDsa.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Core.dll
+LIB_REFS = System System.Core
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 26d1d81df8097a7ab2b9d711f3674cc949b7ce0f..0e8b16442809185da2b5cbbd1360e5d6179ef6d7 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.Encryption.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e146e689b9771f847bdbddbd1cdbec3fef37e7c3..45dad5331da23e4452f0c252b3a388870f1eb3c4 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.Hashing.Algorithms.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 450bb596fd866717afb7f142bc914b02ce12a80b..9df5800609b98319608e55b58dd3b6579ff61ba9 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.Hashing.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index f82c860416253a13030c5d35a30a5049c7a540b9..1cdbf1de8f3decb38ad50b6f289edf3d0ecdece2 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Security.Cryptography.ProtectedData.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Security.dll
+LIB_REFS = System System.Security
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index a88e14ef6cc0dbbc3879cc0836347dd1401bade5..ea7df7a042ad62c9639d3c530aa08f154aeb648d 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.RSA.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index d9fdec015a2853bf6591d0d2b8bb3386e067fb98..2ffcdbc236f40d94b2eeb61092344223b2c593e0 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.RandomNumberGenerator.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 911aa9fd26809df82d0a84e05d3316cd939dbd46..5ad2d813f95f024e4a80de3a6e15c9458230b531 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Cryptography.X509Certificates.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 8284f5fd5ba3a6e7d3478e9a83c425fc8e546d70..a287f05cb84ff339c878bdd67fed4c535bcff718 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.Principal.Windows.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index c4db680014922ad7d1a4320932584cd5d56eb691..1a1265a0e0571e49dac2d921ebeb481e2f287253 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Security.Principal.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index fb949fbe07e8e40b7b59c5bb96cb2fac21b685f5..b33d20dc20261912e900021303cca36c3d41bda3 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Security.SecureString.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 90f55a71d5eb9168513708b07cc5fab8d7454c7a..a8f568f78b58b0c2fa004f9c5efa73db345a3b76 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ServiceModel.Duplex.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ServiceModel
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 99587810c49caec9570c7cb6cde16120cc562fc1..05f7925c2c66740a9ee27f12489d9e2e73fc10a8 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ServiceModel.Http.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ServiceModel
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index c01e4819efb8fdd94d709a6ca49971c8854025d5..f0af8c7dc6088864b77f302a9f60619ba3cb9170 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ServiceModel.NetTcp.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ServiceModel
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 6f94ff346f87c6ea87d72ee2e5b3f4f32e4d54d2..5f65e0599a30b14d256482f517c0ec7e66a5e4db 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ServiceModel.Primitives.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ServiceModel System.Xml
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 4e572464aa800736c72743cc8eba12301c2bd2f7..f68beafd26e7bb4b12b0d47624ee46a3e4babc93 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.ServiceModel.Security.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.ServiceModel
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 9025a6cd91d1f028b489d5f179ab64dd0975a0a7..2724a34a105c35861c75080253a8dbf96d954e99 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.ServiceProcess.ServiceController.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.ServiceProcess.dll
+LIB_REFS = System System.ServiceProcess
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 114132e3a0fed95137f758c3280942607c68be5d..e851968fdb46f4ea5872733d58708af28e99f521 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Text.Encoding.Extensions.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index aeb003f7bb8810403737dc41b4f80faef827224d..fdfff71849704bb266a05fbd0132cba0818a7080 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Text.Encoding.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 423212c687c95c769db104d74301ac7e4648c234..b345b0d5dcd484cb273644a2f97f5527a1e15200 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Text.RegularExpressions.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 56cf986675d62aa503060f6c9a8578ddb6563781..b0c9264a03b466ee7b50290b3c4b12b5fb140b92 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.AccessControl.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 29dbfe5e191a07be8389120ac3cde1845bb14299..460fb4aff26d042fd0beb0c5b8bb7cd8ced7eb27 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.Overlapped.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1f74d4934d3698e818a16092e451a4b49aa1be56..7e350f61c2acd2c8ae208c847eb2e76a22427d3d 100644 (file)
@@ -11,7 +11,7 @@ LIBRARY = System.Threading.Tasks.Parallel.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index c89db2377a85d6f7038bd6d382659d0814225f88..deea2c66a8a2cb9ddec8ba6e75ffeb52203f6af2 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.Tasks.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 177e8890f9f3a4ae66a69b6c8bbeaf8ddd9e838a..cc0bb96aa06b08bbbfa65e9c5b331bafd5a80571 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.Thread.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 67b0082be9eb45a7f2bc53ab978ac782134423b3..604a88c87e7065f9427cf4e430610963436abe7e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.ThreadPool.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 35df02e1825fa6abfa486350d6610baa3b9d6278..5ab3f8409016c7442859ec1cb18d8ebd38b8347e 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.Timer.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 1982ff8384e9ea2d120a49c149c125271ca7e772..b6b5c4cd67b94f12e4fe086238d094da6917ff56 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Threading.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System System.Core
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index 373c1ff882e09ea5f2813bbb97da43f8a7131ae3..27f820f582efa014841e2520d00d2bf79d5fdd0d 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Xml.ReaderWriter.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Xml
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index e55fec5512e39b994298218c5a744dd2f42d218e..79eaaf4424997ed36fae1a6e2819ff5f82446db0 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Xml.XDocument.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Xml.Linq System.Xml
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index ee05487967b100037c597d31a989ec4f46ec68bc..45ffe3482e084120afd9a7685bf6684b584bee83 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Xml.XPath.XDocument.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Xml.Linq.dll
+LIB_REFS = System System.Xml.Linq
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 86a093ba7ad96381ac707493d035fec55368bf6d..7a7ebf6de9d82973eadd8dac53399cf398d5630f 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Xml.XPath.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Xml.dll
+LIB_REFS = System System.Xml
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 68224f9f25fc2ddfc202bae61e11053f3299cafe..8628579f2f12557479e7a490377ff041f4506371 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Xml.XmlDocument.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Xml.dll
+LIB_REFS = System System.Xml
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 3a1e1396f75e7777c6f502807a016ebdb931a45a..f8c09af8c35d9f2ceaf74aac97f3f9f0c2d6afa1 100644 (file)
@@ -12,7 +12,7 @@ LIBRARY = System.Xml.XmlSerializer.dll
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
 LIB_REFS = System.Xml
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll
+LIB_MCS_FLAGS = $(SIGN_FLAGS) 
 
 PLATFORM_DEBUG_FLAGS =
 
index d038a8d5840d941fd48ecde2056776e6492a1beb..abddd14886e03137b45f4bc0b9b742496446bfcc 100644 (file)
@@ -11,8 +11,8 @@ LIBRARY = System.Xml.Xsl.Primitives.dll
 
 KEY_FILE = ../../msfinal.pub
 SIGN_FLAGS = /delaysign /keyfile:$(KEY_FILE) /nowarn:1616,1699
-LIB_REFS = System
-LIB_MCS_FLAGS = $(SIGN_FLAGS) /r:mscorlib.dll /r:System.Xml.dll
+LIB_REFS = System System.Xml
+LIB_MCS_FLAGS = $(SIGN_FLAGS)
 
 PLATFORM_DEBUG_FLAGS =
 
index 753b2a36b14bdea8a29b5da3bfbad8f556803c47..3ace52300071ba004f33be384f5ad5842c827f8a 100644 (file)
@@ -690,7 +690,7 @@ namespace I18N.CJK
                                                // am so lazy, so reusing jis2sjis
                                                int s1 = ((bytes [i] - 1) >> 1) + ((bytes [i] <= 0x5e) ? 0x71 : 0xb1);
                                                int s2 = bytes [i + 1] + (((bytes [i] & 1) != 0) ? 0x20 : 0x7e);
-                                               int v = (s1 - 0x81) * 0xBC;
+                                               int v = (s1 <= 0x9F ? (s1 - 0x81) : (s1 - 0xc1)) * 0xBC;
                                                v += s2 - 0x41;
 
                                                int ch = ToChar (v);
index 9d6c885099cefc9977a2be3b657c859db4e1dcb5..e5b85c14f00e175c866a1a4669d514a8218accaa 100644 (file)
@@ -3,7 +3,9 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.CJK.dll
-LOCAL_MCS_FLAGS = /unsafe /resource:big5.table /resource:gb2312.table /resource:jis.table /resource:ks.table /resource:gb18030.table /r:$(corlib) /r:I18N.dll /define:DISABLE_UNSAFE
+LIB_REFS = I18N
+LOCAL_MCS_FLAGS = /unsafe /resource:big5.table /resource:gb2312.table /resource:jis.table /resource:ks.table /resource:gb18030.table /define:DISABLE_UNSAFE
+TEST_LIB_REFS = I18N
 
 EXTRA_DISTFILES = big5.table jis.table gb2312.table ks.table gb18030.table \
        README.gb18030 \
index ccfe7f457eb559f210a084a5e378651cf861b3c8..afe619503c1b9ba6c784b874839a17953f9f2c8e 100644 (file)
@@ -1,4 +1,5 @@
 \e$BF|K\8lJQ49$N\e(IC=B\e$B"+H>3Q\e(I6E\e$B$b\e(I!T/B9@^H\e(B
+[\e$BlM\e(B]
 
 Mono Directions
 
index da85bfa269d622e8c4968edd3a81236f84d8f3f3..fb2df61a8416d2f2945758685b7636da40942a7d 100644 (file)
@@ -1,4 +1,5 @@
 \e$BF|K\8lJQ49$N\ eC=B\ f"+H>3Q\ e6E\ f$b\ e!T/B9@^H\ f\e(B
+[\e$BlM\e(B]
 
 Mono Directions
 
index c1f06116fbd6452e4dd6448577df1ce0f45992ee..0fd82733278b67a285ecd48da57500e4b27de5e0 100644 (file)
@@ -1,4 +1,5 @@
 ÆüËܸìÊÑ´¹¤Î\8eÃ\8e½\8e¢«È¾³Ñ\8e\8eŤâ\8e¡\8eÔ\8e¯\8eÂ\8e¹\8eÀ\8eÞ\8eÈ
+[ìÍ]
 
 Mono Directions
 
index 596ca1c897f1372164d4602758529a14eb486f1e..21a41ba30e5b319391868f7df5b08666e8e88e33 100644 (file)
@@ -1,4 +1,5 @@
 \93ú\96{\8cê\95Ï\8a·\82ÌýÂ\81©\94¼\8ap¶Å\82à¡Ô¯Â¹ÀÞÈ
+[æË]
 
 Mono Directions
 
index 3b8c4bdcae341bbed3fde8d36dfc06f914a1a65a..bfb79bf6098d6b0bdebac49e81a907d1b74f54d6 100644 (file)
@@ -1,4 +1,5 @@
 日本語変換のテスツ←半角カナも。ヤッツケダネ
+[賤]
 
 Mono Directions
 
index af1aa401cd540d337743de75df02a68dcde2a914..b68973bdc26d306d50fbd3015329e547b33519f3 100644 (file)
@@ -3,7 +3,7 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.dll
-LOCAL_MCS_FLAGS = /r:$(corlib) /unsafe /define:DISABLE_UNSAFE
+LOCAL_MCS_FLAGS = /unsafe /define:DISABLE_UNSAFE
 NO_TEST = yes
 
 include ../../../build/library.make
index aafe245f6a451fb417b2830e9e16d9c69d73eafd..1872c831e58291d947e74991686bf28cee8764ff 100644 (file)
@@ -3,8 +3,9 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.MidEast.dll
-LOCAL_MCS_FLAGS = /r:$(corlib) /r:I18N.dll /unsafe
-#NO_TEST = yes
+LIB_REFS = I18N
+LOCAL_MCS_FLAGS = /unsafe
+TEST_LIB_REFS = I18N
 
 EXTRA_DISTFILES = $(wildcard *.ucm) \
        $(wildcard Test/texts/*.txt)
index e5740f32cb6cd1d248e8c29e3887530fc4e02a3d..47fac195ad91e2e7fc8153446f289c74d2aa8260 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.Other.dll
-LOCAL_MCS_FLAGS = /r:$(corlib) /r:I18N.dll /unsafe
+LIB_REFS = I18N
+LOCAL_MCS_FLAGS = /unsafe
 NO_TEST = yes
 
 EXTRA_DISTFILES = $(wildcard *.ucm)
index fd315cfce147139cbdb02f64a060a34320ce283a..f558e20e555a7ac67077770c20b82913d4743ef6 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.Rare.dll
-LOCAL_MCS_FLAGS = /r:$(corlib) /r:I18N.dll /unsafe
+LIB_REFS = I18N
+LOCAL_MCS_FLAGS = /unsafe
 NO_TEST = yes
 
 EXTRA_DISTFILES = $(wildcard *.ucm)
index e8b7afe3d0732c1589f0ee5ab59e551a4a953cd5..bc4b2386188478bf070d57a2a90973b2a6b08cc7 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../../build/rules.make
 
 LIBRARY = I18N.West.dll
-LOCAL_MCS_FLAGS = /r:$(corlib) /r:I18N.dll /unsafe
+LIB_REFS = I18N
+LOCAL_MCS_FLAGS = /unsafe
 #NO_TEST = yes
 
 EXTRA_DISTFILES = $(wildcard *.ucm) \
index 732087d903e16fd8ff8484e352dd2440285fe2e0..630df027785d0286fa1c729208e98a65a39d4a69 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = IBM.Data.DB2.dll
 LIB_REFS = System System.Xml System.Data
-LIB_MCS_FLAGS = /unsafe /r:$(corlib) -warn:1
+LIB_MCS_FLAGS = /unsafe -warn:1
 NO_TEST = yes
 
 EXTRA_DISTFILES = ibm.pub
index 6a4052c5577796fcaffcaae252c9f334c9244693..bd64d2a4d66c7b991e6609fc8547288ec40a3bd3 100644 (file)
@@ -6,7 +6,7 @@ LIBRARY = ICSharpCode.SharpZipLib.dll
 LIBRARY_SNK = SharpZipLib.key
 
 LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = /r:$(corlib) -warn:1
+LIB_MCS_FLAGS = -warn:1
 NO_TEST = yes
 EXTRA_DISTFILES = SharpZipLib.pub $(LIBRARY_SNK)
 
index ee6e39dcc86cb40c84c98bcbdc0d8f55beacdf35..167bc4ca5cc5bc8a883aa8d145b3c9249aba47b0 100644 (file)
@@ -1,8 +1,6 @@
 thisdir = class
 
-# Note that Mono.Security and System.Security aren't listed.
-# We may have to add those if 'mcs' starts using them.
-basic_SUBDIRS := corlib System System.XML System Mono.Security System.Core 
+basic_SUBDIRS := corlib Mono.Security System System.XML System.Core 
 
 # resgen is corlib specific so we need to wait until corlib is build
 # and build it just a step before first dll needs it
@@ -10,21 +8,22 @@ resgen_dir = ../tools/resgen
 
 build_SUBDIRS :=  \
        corlib \
+       Mono.Security \
        System \
        System.XML \
-       System Mono.Security \
        Mono.Posix \
-       System.Core
+       System.Core \
+       Mono.Cecil \
+       Mono.Cecil.Mdb
 
 pcl_facade_dirs := Facades
 
 mobile_common_dirs := \
        corlib  \
+       Mono.Security \
        System  \
        System.Core     \
        System.XML      \
-       Mono.Security   \
-       System  \
        I18N            \
        System.ServiceModel.Internals   \
        SMDiagnostics   \
@@ -80,6 +79,7 @@ monotouch_tv_dirs   := $(monotouch_dirs)
 
 monotouch_runtime_dirs := \
        corlib \
+       Mono.Security \
        System \
        System.Core \
        System.XML \
@@ -90,12 +90,11 @@ monotouch_tv_runtime_dirs := $(monotouch_runtime_dirs)
 
 xammac_4_5_dirs := \
        corlib  \
+       Mono.Security \
        System  \
        Mono.Posix                      \
        System.Core     \
        System.XML      \
-       Mono.Security   \
-       System  \
        I18N            \
        System.ServiceModel.Internals   \
        SMDiagnostics   \
@@ -138,12 +137,12 @@ xammac_4_5_dirs := \
 
 net_4_x_dirs := \
        corlib                          \
+       Mono.Security \
        System                          \
        System.XML                      \
        Mono.CompilerServices.SymbolWriter \
        Mono.Posix                      \
        System.Core                     \
-       Mono.Security                   \
        System.Security                 \
        System.Configuration    \
        $(resgen_dir)                   \
@@ -270,6 +269,12 @@ net_4_x_parallel_dirs := \
        Microsoft.VisualC               \
        WebMatrix.Data \
        monodoc \
+       System.Deployment \
+       System.Web.Mobile \
+       System.Web.RegularExpressions \
+       System.Workflow.Activities \
+       System.Workflow.ComponentModel \
+       System.Workflow.Runtime \
        $(pcl_facade_dirs)
 
 xbuild_2_0_dirs := \
index 47216dc7d240adcdc7aff86163e6c1514107b056..9aed81206542d94d4976f0974107b89d405a8e89 100644 (file)
@@ -7,38 +7,28 @@ include $(XBUILD_DIR)/xbuild.make
 
 LIBRARY = Microsoft.Build.Engine.dll
 
-LIB_REFS = System System.Core System.Xml
-LIB_MCS_FLAGS = \
-       /r:$(corlib)            \
-       /r:System.dll           \
-       /r:System.Core.dll      \
-       /r:System.Xml.dll       \
-       /r:$(XBUILD_FRAMEWORK)  \
-       /r:$(XBUILD_UTILITIES)
-
-TEST_MCS_FLAGS = \
-       /r:$(XBUILD_FRAMEWORK)  \
-       /r:$(XBUILD_UTILITIES) \
-       /r:System.Xml.dll
+LIB_REFS = $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core $(PARENT_PROFILE)System.Xml $(XBUILD_FRAMEWORK) $(XBUILD_UTILITIES)
+LIB_MCS_FLAGS =
+
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = $(XBUILD_FRAMEWORK) $(XBUILD_UTILITIES) $(PARENT_PROFILE)System.Xml
 
 EXTRA_DISTFILES = \
        Test/resources/TestTasks.cs             \
        Test/resources/*.*proj  \
        Test/resources/*.csproj
 
-Test/resources/TestTasks-$(PROFILE).dll: Test/resources/TestTasks.cs
-       $(CSCOMPILE) /out:$@ Test/resources/TestTasks.cs /r:$(XBUILD_FRAMEWORK) /r:$(XBUILD_UTILITIES) /target:library
+CLEAN_FILES = Test/resources/TestTasks-$(PROFILE).dll Test/resources/TestTasks-$(PROFILE).dll.mdb Test/resources/TestTasks-$(PROFILE).pdb
 
-clean-test-resources:
-       rm -f Test/resources/TestTasks*.dll Test/resources/TestTasks*.dll.mdb
+Test/resources/TestTasks-$(PROFILE).dll: Test/resources/TestTasks.cs
+       $(CSCOMPILE) /out:$@ Test/resources/TestTasks.cs /r:$(topdir)/class/lib/$(PROFILE)/$(XBUILD_FRAMEWORK).dll /r:$(topdir)/class/lib/$(PROFILE)/$(XBUILD_UTILITIES).dll /target:library
 
 test-local: compile-resources
 
 compile-resources: Test/resources/TestTasks-$(PROFILE).dll
        cp Test/resources/TestTasks-$(PROFILE).dll Test/resources/TestTasks.dll
        cp Test/resources/TestTasks-$(PROFILE).dll.mdb Test/resources/TestTasks.dll.mdb
-
-clean-local: clean-test-resources
+#      cp Test/resources/TestTasks-$(PROFILE).pdb Test/resources/TestTasks.pdb
 
 include $(XBUILD_DIR)/xbuild_test.make
 include ../../build/library.make
index 779dc9e2fd40f9df98f2e3dfdc2ed60fb4817198..f31f5a5835ea5f0b8f33c7bdfc059a0490a3e8e9 100644 (file)
@@ -7,10 +7,8 @@ include $(XBUILD_DIR)/xbuild.make
 
 LIBRARY = Microsoft.Build.Framework.dll
 
-LIB_REFS = System
-LIB_MCS_FLAGS = \
-       /r:$(corlib)                            \
-       /r:System.dll
+LIB_REFS = $(PARENT_PROFILE)System
+LIB_MCS_FLAGS =
 
 EXTRA_DISTFILES = \
        Mono.XBuild.Framework/AssemblyLoadInfo.cs
index 66b74a847289a6e708a92bb23fa294d3cab2e4bf..d451c754e74471c627da9bbd3e6ffd86fd871a90 100644 (file)
@@ -9,28 +9,14 @@ LIBRARY = Microsoft.Build.Tasks.dll
 
 LIBRARY_NAME = Microsoft.Build.Tasks$(NAME_SUFFIX).dll
 
-LIB_REFS = System System.Core System.Xml System.Windows.Forms
-LIB_MCS_FLAGS = \
-       /r:$(corlib)                            \
-       /r:System.dll                           \
-       /r:System.Core.dll                      \
-       /r:System.Xml.dll                       \
-       /r:System.Windows.Forms.dll             \
-       /r:$(XBUILD_UTILITIES)                  \
-       /r:$(XBUILD_FRAMEWORK)                  \
-       /r:$(XBUILD_ENGINE)                     \
-       /r:$(XBUILD_TASKS)
-
-TEST_MCS_FLAGS = \
-       /r:System.Xml.dll                       \
-       /r:$(XBUILD_ENGINE)     \
-       /r:$(XBUILD_FRAMEWORK)  \
-       /r:$(XBUILD_TASKS)      \
-       /r:$(XBUILD_UTILITIES)                  \
-       /r:System.Core.dll
+LIB_REFS = $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core $(PARENT_PROFILE)System.Xml $(PARENT_PROFILE)System.Windows.Forms \
+                       $(XBUILD_UTILITIES) $(XBUILD_FRAMEWORK) $(XBUILD_ENGINE) $(XBUILD_TASKS)
+
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = $(PARENT_PROFILE)System.Xml $(XBUILD_ENGINE) $(XBUILD_FRAMEWORK) $(XBUILD_TASKS) $(XBUILD_UTILITIES) $(PARENT_PROFILE)System.Core
 
 ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
-       TEST_MCS_FLAGS += /r:Microsoft.Build.dll
+TEST_LIB_REFS += Microsoft.Build
 endif
 
 EXTRA_DISTFILES = \
@@ -41,7 +27,7 @@ EXTRA_DISTFILES = \
        Test/test-config-file*
 
 Test/resources/test.dll: Test/resources/test.cs
-       $(CSCOMPILE) -target:library Test/resources/test.cs
+       $(CSCOMPILE) -target:library /out:$@ $<
 
 clean-test-resources:
        rm -f Test/resources/test.dll
index 6fd7954ab42c949f141c90ef3aeeec886a16c22d..bb85df584df4eb0e8f41e58f61c9a855bacec375 100644 (file)
@@ -41,6 +41,8 @@ namespace Microsoft.Build.Tasks {
                ITaskItem[]     assignedProjects;
                string          solutionConfigurationContents;
                ITaskItem[]     unassignedProjects;
+               Dictionary<Guid, string> guidToConfigPlatform;
+               Dictionary<string, string> absolutePathToConfigPlatform;
        
                public AssignProjectConfiguration ()
                {
@@ -53,10 +55,10 @@ namespace Microsoft.Build.Tasks {
                                return true;
 
                        XmlReader xr = null;
-                       Dictionary<Guid, string> guidToConfigPlatform = null;
+                       guidToConfigPlatform = new Dictionary<Guid, string> ();
+                       absolutePathToConfigPlatform = new Dictionary<string, string> ();
                        try {
                                xr = XmlReader.Create (new StringReader (solutionConfigurationContents));
-                               guidToConfigPlatform = new Dictionary<Guid, string> ();
 
                                xr.Read ();
                                while (!xr.EOF) {
@@ -65,12 +67,20 @@ namespace Microsoft.Build.Tasks {
                                                continue;
 
                                        string guid_str = xr.GetAttribute ("Project");
+                                       string abs_path = xr.GetAttribute ("AbsolutePath");
                                        string config_str = xr.ReadString ();
 
+                                       if (String.IsNullOrEmpty (config_str))
+                                               continue;
+
                                        Guid guid;
-                                       if (!String.IsNullOrEmpty (guid_str) && !String.IsNullOrEmpty (config_str) &&
-                                               TryParseGuid (guid_str, out guid))
+                                       if (TryParseGuid (guid_str, out guid))
                                                guidToConfigPlatform [guid] = config_str;
+
+                                       if (!String.IsNullOrEmpty (abs_path)) {
+                                               abs_path = Path.GetFullPath (abs_path);
+                                               absolutePathToConfigPlatform [abs_path] = config_str;
+                                       }
                                }
                        } catch (XmlException xe) {
                                Log.LogError ("XmlException while parsing SolutionConfigurationContents: {0}",
@@ -84,32 +94,22 @@ namespace Microsoft.Build.Tasks {
                        List<ITaskItem> tempAssignedProjects = new List<ITaskItem> ();
                        List<ITaskItem> tempUnassignedProjects = new List<ITaskItem> ();
                        foreach (ITaskItem item in ProjectReferences) {
-                               string config;
-
-                               string guid_str = item.GetMetadata ("Project");
+                               string config = GetConfigPlatformFromProjectReference (item);
 
-                               Guid guid = Guid.Empty;
-                               if (!string.IsNullOrEmpty(guid_str) && !TryParseGuid (guid_str, out guid)) {
-                                       Log.LogError ("Project reference '{0}' has invalid or missing guid for metadata 'Project'.",
-                                                       item.ItemSpec);
-                                       return false;
+                               if (String.IsNullOrEmpty (config)) {
+                                       tempUnassignedProjects.Add (item);
+                                       continue;
                                }
 
-                               if (guid != Guid.Empty && guidToConfigPlatform.TryGetValue (guid, out config)) {
-                                       string [] parts = config.Split (new char [] {'|'}, 2);
+                               string [] parts = config.Split (new char [] {'|'}, 2);
 
-                                       ITaskItem new_item = new TaskItem (item);
+                               ITaskItem new_item = new TaskItem (item);
 
-                                       new_item.SetMetadata ("SetConfiguration", "Configuration=" + parts [0]);
-                                       new_item.SetMetadata ("SetPlatform", "Platform=" +
-                                                       ((parts.Length > 1) ? parts [1] : String.Empty));
+                               new_item.SetMetadata ("SetConfiguration", "Configuration=" + parts [0]);
+                               new_item.SetMetadata ("SetPlatform", "Platform=" +
+                                               ((parts.Length > 1) ? parts [1] : String.Empty));
 
-                                       tempAssignedProjects.Add (new_item);
-                               } else {
-                                       Log.LogWarning ("Project reference '{0}' could not be resolved.",
-                                                       item.ItemSpec);
-                                       tempUnassignedProjects.Add (item);
-                               }
+                               tempAssignedProjects.Add (new_item);
                        }
 
                        assignedProjects = tempAssignedProjects.ToArray ();
@@ -118,9 +118,29 @@ namespace Microsoft.Build.Tasks {
                        return true;
                }
 
+               string GetConfigPlatformFromProjectReference (ITaskItem item)
+               {
+                       string guid_str = item.GetMetadata ("Project");
+                       string proj_full_path = item.GetMetadata ("FullPath");
+
+                       string config;
+                       Guid guid = Guid.Empty;
+                       if (TryParseGuid (guid_str, out guid) && guidToConfigPlatform.TryGetValue (guid, out config))
+                               return config;
+
+                       string abs_path = item.GetMetadata ("FullPath");
+                       if (absolutePathToConfigPlatform.TryGetValue (abs_path, out config))
+                               return config;
+
+                       return null;
+               }
+
                bool TryParseGuid (string guid_str, out Guid guid)
                {
                        guid = Guid.Empty;
+                       if (String.IsNullOrEmpty (guid_str))
+                               return false;
+
                        try {
                                guid = new Guid (guid_str);
                        } catch (ArgumentNullException) {
index 2102d41c3f32708d5536d74f87741b8fb7acc8d9..9d759e09d9d5be9fd8a72b9326d19cfcee53253c 100644 (file)
@@ -185,7 +185,7 @@ namespace Microsoft.Build.Tasks
                        var cscParams = new CompilerParameters ();
                        cscParams.ReferencedAssemblies.Add ("Microsoft.Build.Framework.dll");
                        cscParams.ReferencedAssemblies.Add ("Microsoft.Build.Utilities.v4.0.dll"); // since we use Task, it depends on this dll.
-                       cscParams.ReferencedAssemblies.AddRange (references.ToArray ());
+                       cscParams.ReferencedAssemblies.AddRange (GetReferences (references, taskFactoryLoggingHost));
                        cscParams.GenerateInMemory = true;
                        var results = CodeDomProvider.CreateProvider (language).CompileAssemblyFromDom (cscParams, ccu);
                        var errors = new CompilerError [results.Errors.Count];
@@ -197,6 +197,36 @@ namespace Microsoft.Build.Tasks
                        assembly = results.CompiledAssembly;
                        return true;
                }
+
+               static string[] GetReferences (List<string> references, IBuildEngine log)
+               {
+                       var res = new List<string> ();
+                       foreach (var r in references) {
+                               if (File.Exists (r)) {
+                                       res.Add (r);
+                                       continue;
+                               }
+
+                               Assembly assembly = null;
+
+                               try {
+                                       if (!r.EndsWith (".dll", StringComparison.OrdinalIgnoreCase) || !r.EndsWith (".exe", StringComparison.OrdinalIgnoreCase)) {
+                                               assembly = Assembly.LoadWithPartialName (r);
+                                       }
+
+                                       if (assembly != null) {
+                                               res.Add (assembly.Location);
+                                               continue;
+                                       }
+                               } catch {
+                               }
+
+                               log.LogErrorEvent (new BuildErrorEventArgs ("", "", "", 0, 0, 0, 0, "Assembly reference {r} could not be resolved", "", ""));
+                       }
+
+                       return res.ToArray ();
+               }
+
                public string FactoryName {
                        get { return "Code Task Factory"; }
                }
index f7d25591a8ce8973f4046ed5dbb53331841463c1..be1ea2c0fb787a177fcd0c7f659e97df04b10427 100644 (file)
@@ -32,6 +32,7 @@ using Microsoft.Build.Framework;
 using Microsoft.Build.Tasks;
 using Microsoft.Build.Utilities;
 using NUnit.Framework;
+using System.IO;
 using System.Text;
 
 namespace MonoTests.Microsoft.Build.Tasks
@@ -58,22 +59,73 @@ namespace MonoTests.Microsoft.Build.Tasks
                                "{DAE34193-B5C7-4488-A911-29EE15C84CBE}"
                        };
 
-                       CreateAndCheckProject (guids, project_ref_guids, new string[] {
-                                       "AssignedProjects : foo0.csproj;foo1.csproj;foo2.csproj;foo3.csproj: SetConfig: Configuration=Release",
+                       CreateAndCheckProject (guids, new bool[] {true, true, true, true, true, true},
+                                       project_ref_guids, new string[] {
+                                       "AssignedProjects : foo0.csproj;foo1.csproj;foo2.csproj;foo3.csproj;foo4.csproj: SetConfig: Configuration=Release",
                                        "AssignedProjects : foo0.csproj: SetPlatform: Platform=AnyCPU0",
                                        "AssignedProjects : foo1.csproj: SetPlatform: Platform=AnyCPU1",
                                        "AssignedProjects : foo2.csproj: SetPlatform: Platform=AnyCPU2",
                                        "AssignedProjects : foo3.csproj: SetPlatform: Platform=AnyCPU3",
-                                       "UnassignedProjects : foo4.csproj"},
+                                       "AssignedProjects : foo4.csproj: SetPlatform: Platform=AnyCPU4",
+                                       "UnassignedProjects : "},
                                        true,
                                         "A1#");
                }
 
                [Test]
-               public void TestInvalidProjectGuid ()
+               public void TestNoGuidAndNoAbsolutePathFound()
                {
                        string[] guids = new string[] {
+                               "asd"
+                       };
+
+                       string[] project_ref_guids = new string[] {
+                               "{DAE34193-B5C7-4488-A911-29EE15C84CB8}",
+                               "invalid guid",
+                               ""
+                       };
+
+                       CreateAndCheckProject (guids, new bool[]{false},
+                                       project_ref_guids,
+                                       new string[] {
+                                               "AssignedProjects : : SetConfig: ",
+                                               "AssignedProjects : : SetPlatform: ",
+                                               "UnassignedProjects : foo0.csproj;foo1.csproj;foo2.csproj"
+                                       },
+                                       true, "A1#");
+               }
+
+               [Test]
+               public void TestInvalidProjectGuidWithAbsolutePath ()
+               {
+                       string[] guids = new string[] {
+                               null, // no AbsPath
+                               "another invalid guid", // has AbsPath
+                       };
+
+                       string[] project_ref_guids = new string[] {
+                               "1234zxc", // this won't match because no AbsPath
+                               "xzxoiu",  // match with the second project, foo1.csproj
                                "{23F291D9-78DF-4133-8CF2-78CE104DDE63}",
+                               "badref"   // no corresponding project at all
+                       };
+
+                       CreateAndCheckProject (guids, new bool[]{false, true},
+                                       project_ref_guids,
+                                       new string[] {
+                                               "AssignedProjects : foo1.csproj: SetConfig: Configuration=Release",
+                                               "AssignedProjects : foo1.csproj: SetPlatform: Platform=AnyCPU1",
+                                               "UnassignedProjects : foo0.csproj;foo2.csproj;foo3.csproj"
+                                       },
+                                       true, "A1#");
+               }
+
+               [Test]
+               public void TestNoGuidWithAbsolutePath ()
+               {
+                       string[] guids = new string[] {
+                               "",
+                               null
                        };
 
                        string[] project_ref_guids = new string[] {
@@ -82,7 +134,14 @@ namespace MonoTests.Microsoft.Build.Tasks
                                "invalid guid"
                        };
 
-                       CreateAndCheckProject (guids, project_ref_guids, null, false, "A1#");
+                       CreateAndCheckProject (guids, new bool[]{true, false},
+                                       project_ref_guids,
+                                       new string[] {
+                                               "AssignedProjects : foo0.csproj: SetConfig: Configuration=Release",
+                                               "AssignedProjects : foo0.csproj: SetPlatform: Platform=AnyCPU0",
+                                               "UnassignedProjects : foo1.csproj;foo2.csproj"
+                                       },
+                                       true, "A1#");
                }
 
                [Test]
@@ -97,7 +156,8 @@ namespace MonoTests.Microsoft.Build.Tasks
                                "{23F291D9-78DF-4133-8CF2-78CE104DDE63}"
                        };
 
-                       CreateAndCheckProject (guids, project_ref_guids,
+                       CreateAndCheckProject (guids, new bool[]{false, true},
+                               project_ref_guids,
                                new string [] {
                                        "AssignedProjects : foo1.csproj: SetConfig: Configuration=Release",
                                        "AssignedProjects : foo1.csproj: SetPlatform: Platform=AnyCPU0",
@@ -106,14 +166,14 @@ namespace MonoTests.Microsoft.Build.Tasks
                }
 
 
-               void CreateAndCheckProject (string[] guids, string[] project_ref_guids, string[] messages, bool build_result, string prefix)
+               void CreateAndCheckProject (string[] guids, bool[] set_project_paths, string[] project_ref_guids, string[] messages, bool build_result, string prefix)
                {
                        Engine engine = new Engine (Consts.BinPath);
                        Project project = engine.CreateNewProject ();
                        TestMessageLogger testLogger = new TestMessageLogger ();
                        engine.RegisterLogger (testLogger);
 
-                       string projectString = CreateProject (guids, project_ref_guids);
+                       string projectString = CreateProject (guids, set_project_paths, project_ref_guids);
                        project.LoadXml (projectString);
 
                        try {
@@ -131,12 +191,12 @@ namespace MonoTests.Microsoft.Build.Tasks
                        }
                }
 
-               string CreateProject (string[] guids, string[] project_ref_guids)
+               string CreateProject (string[] guids, bool[] set_project_paths, string[] project_ref_guids)
                {
                        StringBuilder sb = new StringBuilder ();
                        sb.Append (@"<Project xmlns=""http://schemas.microsoft.com/developer/msbuild/2003"">");
                        sb.Append ("\n" + GetUsingTask ("AssignProjectConfiguration"));
-                       sb.AppendFormat (@"<PropertyGroup>{0}</PropertyGroup>", CreateSolutionConfigurationProperty (guids, "Release|AnyCPU"));
+                       sb.AppendFormat (@"<PropertyGroup>{0}</PropertyGroup>", CreateSolutionConfigurationProperty (guids, set_project_paths, "Release|AnyCPU"));
                        sb.Append (CreateProjectReferencesItemGroup (project_ref_guids));
 
                        sb.Append ("\n\t<Target Name=\"1\">\n");
@@ -154,13 +214,19 @@ namespace MonoTests.Microsoft.Build.Tasks
                        return sb.ToString ();
                }
 
-               string CreateSolutionConfigurationProperty (string[] guids, string config_str)
+               string CreateSolutionConfigurationProperty (string[] guids, bool[] set_project_paths, string config_str)
                {
+                       string abs_proj_path_prefix = Path.GetFullPath ("foo");
                        StringBuilder sb = new StringBuilder ();
                        sb.Append ("\n<CurrentSolutionConfigurationContents>\n");
                                sb.Append ("\t<foo xmlns=\"\">\n");
                                for (int i = 0; i < guids.Length; i++) {
-                                       sb.AppendFormat ("\t\t<bar Project=\"{0}\">{1}{2}</bar>\n",
+                                       sb.Append ("\t\t<bar");
+                                       if (guids[i] != null)
+                                               sb.AppendFormat (" Project=\"{0}\"", guids[i]);
+                                       if (set_project_paths[i])
+                                               sb.AppendFormat (" AbsolutePath=\"{0}{1}.csproj\" ", abs_proj_path_prefix, i);
+                                       sb.AppendFormat (">{1}{2}</bar>\n",
                                                guids[i], config_str, i);
                                }
                                sb.Append ("\t</foo>\n");
@@ -173,8 +239,12 @@ namespace MonoTests.Microsoft.Build.Tasks
                {
                        StringBuilder sb = new StringBuilder ();
                        sb.Append ("\n<ItemGroup>\n");
-                       for (int i = 0; i < guids.Length; i ++)
-                               sb.AppendFormat ("\t<ProjectReference Include=\"foo{1}.csproj\"><Project>{0}</Project></ProjectReference>\n", guids [i], i);
+                       for (int i = 0; i < guids.Length; i ++) {
+                               sb.AppendFormat ("\t<ProjectReference Include=\"foo{0}.csproj\">", i);
+                               if (guids[i] != null)
+                                       sb.AppendFormat ("<Project>{0}</Project>", guids[i]);
+                               sb.Append ("</ProjectReference>\n");
+                       }
                        sb.Append ("</ItemGroup>\n");
                        return sb.ToString ();
                }
index e44bbc2fe80a85d6b9b06961e073b20b66097b3a..10ef6780d4af6caf04ee40b279df2c40a3915ad6 100644 (file)
@@ -8,17 +8,13 @@ include $(XBUILD_DIR)/xbuild.make
 LIBRARY = Microsoft.Build.Utilities.dll
 LIBRARY_NAME = Microsoft.Build.Utilities$(NAME_SUFFIX).dll
 
-LIB_REFS = System System.Core System.Xml
-LIB_MCS_FLAGS = \
-       /r:$(corlib)                            \
-       /r:System.dll                           \
-       /r:System.Core.dll                      \
-       /r:System.Xml.dll                       \
-       /r:$(XBUILD_FRAMEWORK)
+LIB_REFS = $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core $(PARENT_PROFILE)System.Xml $(XBUILD_FRAMEWORK)
+LIB_MCS_FLAGS =
 
 TEST_RESX_RESOURCES = Test/Microsoft.Build.Utilities/Strings.resources
 
-TEST_MCS_FLAGS = /r:$(XBUILD_ENGINE) /r:$(XBUILD_FRAMEWORK) -r:System.dll -r:System.Core.dll $(TEST_RESX_RESOURCES:%=-resource:%)
+TEST_LIB_REFS = $(XBUILD_ENGINE) $(XBUILD_FRAMEWORK) $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core
+TEST_MCS_FLAGS = $(TEST_RESX_RESOURCES:%=-resource:%)
 
 include $(XBUILD_DIR)/xbuild_test.make
 include ../../build/library.make
@@ -27,6 +23,8 @@ EXTRA_DISTFILES = $(TEST_RESX_RESOURCES:.resources=.resx)
 
 CLEAN_FILES += $(TEST_RESX_RESOURCES)
 
+.NOTPARALLEL: $(TEST_RESX_RESOURCES)
+
 $(TEST_RESX_RESOURCES): %.resources: %.resx
        $(RESGEN) $< || cp $@.prebuilt $@
 
index 68cd09eb0431b5ef865d8b5197a966ec6e25834a..933782ff268b64d48a5d746d2223c93ffee7d39c 100644 (file)
@@ -7,18 +7,12 @@ include $(XBUILD_DIR)/xbuild.make
 
 LIBRARY = Microsoft.Build.dll
 
-LIB_REFS = System System.Core System.Xml Microsoft.Build.Engine Microsoft.Build.Framework
+LIB_REFS = $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core $(PARENT_PROFILE)System.Xml Microsoft.Build.Engine Microsoft.Build.Framework
 LIB_MCS_FLAGS = \
-       /r:$(corlib)                            \
-       /r:System.dll                           \
-       /r:System.Core.dll                      \
-       /r:System.Xml.dll                       \
-       /r:Microsoft.Build.Engine.dll           \
-       /r:Microsoft.Build.Framework.dll        \
        /d:MICROSOFT_BUILD_DLL
        
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) \
-       /r:Microsoft.Build.Utilities.v4.0.dll
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
+TEST_LIB_REFS = $(XBUILD_UTILITIES)
 
 EXTRA_DISTFILES = \
        Microsoft.Build.Internal/ExpressionParser.jay   \
index bd3c641856d7cd133f9488a37de707a989fff58c..c295d3ba67f30a6ead7b70938f594380a009c5f6 100644 (file)
@@ -54,7 +54,8 @@ namespace Microsoft.Build.Execution
                
                public void Dispose ()
                {
-                       WaitHandle.WaitAll (submissions.Select (s => s.WaitHandle).ToArray ());
+                       if (submissions.Count > 0)
+                               WaitHandle.WaitAll (submissions.Select (s => s.WaitHandle).ToArray ());
                        BuildNodeManager.Stop ();
                }
 
index d4414a9b8a5da54340028545decaf7a2ce21c9b4..64cfacd9a49d4b57e4e7db27609369035deda62c 100644 (file)
@@ -427,6 +427,7 @@ namespace Microsoft.Build.Execution
                        };
                        var requestData = new BuildRequestData (this, targets ?? DefaultTargets.ToArray ());
                        var result = manager.Build (parameters, requestData);
+                       manager.Dispose ();
                        targetOutputs = result.ResultsByTarget;
                        return result.OverallResult == BuildResultCode.Success;
                }
index ebfad5ba752ff0ec11cd51eb452d64bb8a186b62..322006a4e849fadd25b24ad978fb62530d9fe27e 100644 (file)
@@ -41,7 +41,10 @@ namespace Microsoft.Build.Internal
                public BuildNodeManager (BuildManager buildManager)
                {
                        BuildManager = buildManager;
-                       new Thread (RunLoop).Start ();
+                       new Thread (RunLoop) {
+                               IsBackground = true,
+                               Name = "xbuild request handler"
+                       }.Start ();
                }
 
                ~BuildNodeManager ()
index 4110234a9803d8022b090bc1c2b724fac5825921..5d38210947f1d5370be2d19a2b626f56450c890e 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Microsoft.VisualC.dll
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index a60df154aebfcee882cb4023e6c9683b76a274d4..316dcc886cdcb804a8eb441fd5f26735fa95d8ef 100644 (file)
-<html>\r
-\r
-<head>\r
-<meta http-equiv=Content-Type content="text/html; charset=windows-1252">\r
-<meta name=Generator content="Microsoft Word 12 (filtered)">\r
-\r
-<style>\r
-<!--\r
- /* Font Definitions */\r
- @font-face\r
-       {font-family:"Cambria Math";\r
-       panose-1:2 4 5 3 5 4 6 3 2 4;}\r
-@font-face\r
-       {font-family:Cambria;\r
-       panose-1:2 4 5 3 5 4 6 3 2 4;}\r
-@font-face\r
-       {font-family:Tahoma;\r
-       panose-1:2 11 6 4 3 5 4 4 2 4;}\r
-@font-face\r
-       {font-family:Verdana;\r
-       panose-1:2 11 6 4 3 5 4 4 2 4;}\r
- /* Style Definitions */\r
- p.MsoNormal, li.MsoNormal, div.MsoNormal\r
-       {margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:12.0pt;\r
-       font-family:"Arial","sans-serif";}\r
-h1\r
-       {mso-style-link:"Heading 1 Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:12.0pt;\r
-       font-family:"Arial","sans-serif";\r
-       font-weight:normal;}\r
-h2\r
-       {mso-style-link:"Heading 2 Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:12.0pt;\r
-       font-family:"Arial","sans-serif";\r
-       font-weight:normal;}\r
-p.MsoCommentText, li.MsoCommentText, div.MsoCommentText\r
-       {mso-style-link:"Comment Text Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:10.0pt;\r
-       font-family:"Arial","sans-serif";}\r
-p.MsoHeader, li.MsoHeader, div.MsoHeader\r
-       {mso-style-link:"Header Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:12.0pt;\r
-       font-family:"Arial","sans-serif";}\r
-p.MsoFooter, li.MsoFooter, div.MsoFooter\r
-       {mso-style-link:"Footer Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:12.0pt;\r
-       font-family:"Arial","sans-serif";}\r
-span.MsoCommentReference\r
-       {font-family:"Times New Roman","serif";}\r
-p.MsoCommentSubject, li.MsoCommentSubject, div.MsoCommentSubject\r
-       {mso-style-link:"Comment Subject Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:10.0pt;\r
-       font-family:"Arial","sans-serif";\r
-       font-weight:bold;}\r
-p.MsoAcetate, li.MsoAcetate, div.MsoAcetate\r
-       {mso-style-link:"Balloon Text Char";\r
-       margin:0in;\r
-       margin-bottom:.0001pt;\r
-       text-autospace:none;\r
-       font-size:8.0pt;\r
-       font-family:"Tahoma","sans-serif";}\r
-span.Heading1Char\r
-       {mso-style-name:"Heading 1 Char";\r
-       mso-style-link:"Heading 1";\r
-       font-family:"Cambria","serif";\r
-       font-weight:bold;}\r
-span.Heading2Char\r
-       {mso-style-name:"Heading 2 Char";\r
-       mso-style-link:"Heading 2";\r
-       font-family:"Cambria","serif";\r
-       font-weight:bold;\r
-       font-style:italic;}\r
-span.BalloonTextChar\r
-       {mso-style-name:"Balloon Text Char";\r
-       mso-style-link:"Balloon Text";\r
-       font-family:"Tahoma","sans-serif";}\r
-span.CommentTextChar\r
-       {mso-style-name:"Comment Text Char";\r
-       mso-style-link:"Comment Text";\r
-       font-family:"Arial","sans-serif";}\r
-span.CommentSubjectChar\r
-       {mso-style-name:"Comment Subject Char";\r
-       mso-style-link:"Comment Subject";\r
-       font-family:"Arial","sans-serif";\r
-       font-weight:bold;}\r
-span.HeaderChar\r
-       {mso-style-name:"Header Char";\r
-       mso-style-link:Header;\r
-       font-family:"Arial","sans-serif";}\r
-span.FooterChar\r
-       {mso-style-name:"Footer Char";\r
-       mso-style-link:Footer;\r
-       font-family:"Arial","sans-serif";}\r
- /* Page Definitions */\r
- @page Section1\r
-       {size:8.5in 11.0in;\r
-       margin:1.0in 1.0in 1.0in 1.0in;}\r
-div.Section1\r
-       {page:Section1;}\r
--->\r
-</style>\r
-\r
-</head>\r
-\r
-<body lang=EN-US style='text-justify-trim:punctuation'>\r
-\r
-<div class=Section1>\r
-\r
-<h1 style='margin-top:9.0pt'><span style='font-size:15.5pt;color:black'>Microsoft\r
-Permissive License (Ms-PL)</span></h1>\r
-\r
-<p class=MsoNormal style='line-height:140%'><b><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>&nbsp;</span></b></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><b><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>This license governs use\r
-of the accompanying software. If you use the software, you accept this license.\r
-If you do not accept the license, do not use the software.</span></b></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>&nbsp;</span></p>\r
-\r
-<h2><b><span style='font-size:11.5pt;font-family:"Verdana","sans-serif"'>1.\r
-Definitions</span></b></h2>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>The terms \93reproduce,\94\r
-\93reproduction,\94 \93derivative works,\94 and \93distribution\94 have the same meaning\r
-here as under U.S. copyright law.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>A \93contribution\94 is the\r
-original software, or any additions or changes to the software.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>A \93contributor\94 is any\r
-person that distributes its contribution under this license.</span></p>\r
-\r
-<p class=MsoNormal><span style='font-size:8.5pt;font-family:"Verdana","sans-serif"'> \93Licensed\r
-patents\94 are a contributor\92s patent claims that read directly on its\r
-contribution.</span></p>\r
-\r
-<h2><b><span style='font-size:11.5pt;font-family:"Verdana","sans-serif"'>&nbsp;</span></b></h2>\r
-\r
-<h2><b><span style='font-size:11.5pt;font-family:"Verdana","sans-serif"'>2.\r
-Grant of Rights</span></b></h2>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(A) Copyright Grant-\r
-Subject to the terms of this license, including the license conditions and\r
-limitations in section 3, each contributor grants you a non-exclusive,\r
-worldwide, royalty-free copyright license to reproduce its contribution,\r
-prepare derivative works of its contribution, and distribute its contribution\r
-or any derivative works that you create.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(B) Patent Grant- Subject\r
-to the terms of this license, including the license conditions and limitations\r
-in section 3, each contributor grants you a non-exclusive, worldwide,\r
-royalty-free license under its licensed patents to make, have made, use, sell,\r
-offer for sale, import, and/or otherwise dispose of its contribution in the\r
-software or derivative works of the contribution in the software.</span></p>\r
-\r
-<h2><b><span style='font-size:11.5pt;font-family:"Verdana","sans-serif"'>&nbsp;</span></b></h2>\r
-\r
-<h2><b><span style='font-size:11.5pt;font-family:"Verdana","sans-serif"'>3.\r
-Conditions and Limitations</span></b></h2>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'> (A) No Trademark License-\r
-This license does not grant you rights to use any contributors\92 name, logo, or\r
-trademarks.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(B) If you bring a patent\r
-claim against any contributor over patents that you claim are infringed by the\r
-software, your patent license from such contributor to the software ends\r
-automatically.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(C) If you distribute any\r
-portion of the software, you must retain all copyright, patent, trademark, and\r
-attribution notices that are present in the software.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(D) If you distribute any\r
-portion of the software in source code form, you may do so only under this\r
-license by including a complete copy of this license with your distribution. If\r
-you distribute any portion of the software in compiled or object code form, you\r
-may only do so under a license that complies with this license.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(E) The software is\r
-licensed \93as-is.\94 You bear the risk of using it. The contributors give no\r
-express warranties, guarantees or conditions. You may have additional consumer\r
-rights under your local laws which this license cannot change. To the extent\r
-permitted under your local laws, the contributors exclude the implied\r
-warranties of merchantability, fitness for a particular purpose and\r
-non-infringement.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>(F) If you distribute the\r
-software or derivative works with programs you develop, you agree to </span><span\r
-style='font-size:8.5pt;line-height:140%;font-family:"Verdana","sans-serif"'>indemnify,\r
-defend, and hold harmless all contributors from any claims, including\r
-attorneys\92 fees, related to the distribution or use of your programs.  For\r
-clarity, you have no such obligations to a contributor for any claims based\r
-solely on the unmodified contributions of that contributor.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'> (G) If you make any\r
-additions or changes to the original software, you may only distribute them\r
-under a new namespace.  In addition, you will clearly identify your changes or\r
-additions as your own.</span></p>\r
-\r
-<p class=MsoNormal style='line-height:140%'><span style='font-size:8.5pt;\r
-line-height:140%;font-family:"Verdana","sans-serif"'>&nbsp;</span></p>\r
-\r
-</div>\r
-\r
-</body>\r
-\r
-</html>\r
+<html>
+
+<head>
+<title>MIT License</title>
+</head>
+
+<body>
+
+<p><b>This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software.</b></p>
+
+<pre>
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+</pre>
+
+</body>
+
+</html>
index 71430e729329903df359647cba9950ff227dd722..c5f80e37114cd2d05a90a1ff92d7ee561a8d1422 100644 (file)
@@ -5,7 +5,7 @@ include ../../build/rules.make
 LIBRARY = Mono.C5.dll
 LIBRARY_SNK = c5.snk
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib) -nowarn:169,219,414,1030,3001,3005,3006
+LIB_MCS_FLAGS = -nowarn:169,219,414,1030,3001,3005,3006
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 
 EXTRA_DISTFILES = \
index 485639075e7f768ebcd5b7863de682bfde32addd..2e7e70305ae1fb4a30d1cde3eaaa3d8c3fc5dd65 100644 (file)
@@ -47,7 +47,7 @@ using System.Runtime.CompilerServices;
 // You can specify all the values or you can default the Revision and Build Numbers 
 // by using the '*' as shown below:
 
-[assembly: AssemblyVersion("1.0.*")]
+[assembly: AssemblyVersion("1.0.0.0")]
 
 //
 // In order to sign your assembly you must specify a key to use. Refer to the 
index 5fe1a18705aa43e4600800f4ed850a216c73066b..d2ed176601d823af3053fa2f8ff4e6b6df0bf2b6 100644 (file)
@@ -15,9 +15,14 @@ ifndef NO_THREAD_ABORT
 REFERENCE_SOURCES_FLAGS += -d:MONO_FEATURE_THREAD_ABORT
 endif
 
-TEST_MCS_FLAGS = -r:System.Core.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Core
 
 LIB_MCS_FLAGS += $(REFERENCE_SOURCES_FLAGS)
 
 include ../../build/library.make
 
+$(topdir)/mcs/cs-parser.cs:
+       $(MAKE) -C $(topdir)/mcs cs-parser.cs
+
+$(the_lib): $(topdir)/mcs/cs-parser.cs
index 70c759c1dab476f0ef70911f277f800221112e34..50357a7903d865a25d955aab0bb58912503f66da 100644 (file)
@@ -6,7 +6,7 @@ LIBRARY_SNK = ../mono.snk
 LIBRARY_PACKAGE = none
 
 LIB_REFS = System Mono.Cecil
-LIB_MCS_FLAGS = /r:$(corlib) /d:CECIL -keyfile:$(LIBRARY_SNK)
+LIB_MCS_FLAGS = /d:CECIL -keyfile:$(LIBRARY_SNK) -publicsign
 
 NO_TEST = yes
 NO_INSTALL = yes
index 790a21809ff02d6f977e5425d24e9289b163a4c8..53aee64f34a11535ec3a8a6bcd875bbba40e0cbf 100644 (file)
@@ -6,7 +6,7 @@ LIBRARY_SNK = ../mono.snk
 LIBRARY_PACKAGE = none
 
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = /r:$(corlib) -keyfile:$(LIBRARY_SNK) -d:NET_3_5
+LIB_MCS_FLAGS = -keyfile:$(LIBRARY_SNK) -d:NET_3_5 /publicsign
 
 NO_TEST = yes
 
index 92a7619d1049ab94c9d42dcd5187db0d9cedae9e..b5e733dbcd989bf7ace531e2e599ce868a1d40a4 100644 (file)
@@ -6,8 +6,8 @@ LIBRARY = Mono.CodeContracts.dll
 
 LIB_REFS = System System.Core Mono.Cecil Mono.Cecil.Mdb
 LIB_MCS_FLAGS =
-#-r:Mono.Cecil.Pdb.dll
 
-TEST_MCS_FLAGS = -r:System.Core.dll -debug
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Core
 
 include ../../build/library.make
index 467436e7e9dfca6b1040dcbe1564f125e2abe983..d30779ce7f13af8b685c1f04fa764222a1556c86 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Mono.CompilerServices.SymbolWriter.dll
 LIB_REFS = System
-LIB_MCS_FLAGS = -lib:$(bare_libdir)
+LIB_MCS_FLAGS =
 
 NO_TEST = yes
 
index 99923147dbbcd0abbe27d020a49bd19e7e8d1cbc..7f35914d241f72792d3667671bf8add783dd3dca 100644 (file)
@@ -33,23 +33,37 @@ namespace Mono.Data.Sqlite
     /// An array of ISO8601 datetime formats we support conversion from\r
     /// </summary>\r
     private static string[] _datetimeFormats = new string[] {\r
+      "THHmmssK",\r
+      "THHmmK",\r
+      "HH:mm:ss.FFFFFFFK",\r
+      "HH:mm:ssK",\r
+      "HH:mmK",\r
+      "yyyy-MM-dd HH:mm:ss.FFFFFFFK", /* NOTE: UTC default (5). */\r
+      "yyyy-MM-dd HH:mm:ssK",\r
+      "yyyy-MM-dd HH:mmK",\r
+      "yyyy-MM-ddTHH:mm:ss.FFFFFFFK",\r
+      "yyyy-MM-ddTHH:mmK",\r
+      "yyyy-MM-ddTHH:mm:ssK",\r
+      "yyyyMMddHHmmssK",\r
+      "yyyyMMddHHmmK",\r
+      "yyyyMMddTHHmmssFFFFFFFK",\r
       "THHmmss",\r
       "THHmm",\r
+      "HH:mm:ss.FFFFFFF",\r
       "HH:mm:ss",\r
       "HH:mm",\r
-      "HH:mm:ss.FFFFFFF",\r
-      "yy-MM-dd",\r
-      "yyyy-MM-dd",\r
-      "yyyy-MM-dd HH:mm:ss.FFFFFFF",\r
+      "yyyy-MM-dd HH:mm:ss.FFFFFFF", /* NOTE: Non-UTC default (19). */\r
       "yyyy-MM-dd HH:mm:ss",\r
-      "yyyy-MM-dd HH:mm",                               \r
+      "yyyy-MM-dd HH:mm",\r
       "yyyy-MM-ddTHH:mm:ss.FFFFFFF",\r
       "yyyy-MM-ddTHH:mm",\r
       "yyyy-MM-ddTHH:mm:ss",\r
       "yyyyMMddHHmmss",\r
       "yyyyMMddHHmm",\r
       "yyyyMMddTHHmmssFFFFFFF",\r
-      "yyyyMMdd"\r
+      "yyyy-MM-dd",\r
+      "yyyyMMdd",\r
+      "yy-MM-dd"\r
     };\r
 \r
     /// <summary>\r
index 4f6cc0ca353c6e4f1a798b176a7b3fb68f2031ed..f1764c2282bff00b3e63a2fbdf97489cb93e5f22 100644 (file)
@@ -4,8 +4,9 @@ include ../../build/rules.make
 
 LIBRARY = Mono.Data.Tds.dll
 LIB_REFS = System System.Xml Mono.Security
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 
-TEST_MCS_FLAGS = /r:System.dll /r:System.Net.dll 
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Net 
 
 include ../../build/library.make
index 659cf71668e2ae51c6e6846d8730e97ce77b1de8..d92fb61f8a9b42622bb75b7adf1437104e2833da 100644 (file)
@@ -5,9 +5,10 @@ LIBRARY = Mono.Debugger.Soft.dll
 LIBRARY_SNK = ../mono.snk
 
 LIB_REFS = System Mono.Cecil System.Core
-LIB_MCS_FLAGS = /r:$(corlib) /unsafe -D:MONO_DATACONVERTER_STATIC_METHODS -keyfile:$(LIBRARY_SNK)
+LIB_MCS_FLAGS = /unsafe -D:MONO_DATACONVERTER_STATIC_METHODS -keyfile:$(LIBRARY_SNK) /publicsign
 
-TEST_MCS_FLAGS = /r:Mono.Cecil.dll /r:System.dll /r:System.Core.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = Mono.Cecil System System.Core
 
 VALID_TEST_PROFILE := $(filter net_4_x, $(PROFILE))
 
@@ -17,7 +18,7 @@ ifdef VALID_TEST_PROFILE
 test-local: dtest-app.exe dtest-excfilter.exe
 
 dtest-app.exe: Test/dtest-app.cs
-       $(CSCOMPILE) -out:$@ -unsafe -debug -optimize- Test/dtest-app.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Core.dll -r:$(topdir)/class/lib/$(PROFILE)/System.dll -out:$@ -unsafe $(PLATFORM_DEBUG_FLAGS) -optimize- Test/dtest-app.cs
 
 dtest-excfilter.exe: Test/dtest-excfilter.il
        MONO_PATH=$(topdir)/class/lib/$(PROFILE) $(INTERNAL_ILASM) -out:$@ /exe /debug Test/dtest-excfilter.il
@@ -29,7 +30,7 @@ check:
 
 endif
 
-CLEAN_FILES = dtest-app.exe dtest-app.exe.mdb dtest-excfilter.exe dtest-excfilter.exe.mdb
+CLEAN_FILES = dtest-app.exe dtest-app.exe.mdb dtest-app.pdb dtest-excfilter.exe dtest-excfilter.exe.mdb dtest-excfilter.pdb
 
 EXTRA_DISTFILES = \
        Test/dtest-app.cs \
index 919f24f0d62cc6c6d81d6cae14996cd8805c73cf..040a1801e1c29afd53171d01eb1a6e6cb9796542 100644 (file)
@@ -4,6 +4,6 @@ include ../../build/rules.make
 
 LIBRARY = Mono.Directory.LDAP.dll
 LIB_REFS = System System.Data
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 
 include ../../build/library.make
index 903006b49b56052e2c2ad929f63327c4ff43e085..6d9565ccbeec7bcc54cb52a404691fa3c3ee9a05 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Mono.Dynamic.Interpreter.dll
 
-LIB_REFS = System System.Core
+LIB_REFS = System
 LIB_MCS_FLAGS = \
        -d:FEATURE_CORE_DLR,FEATURE_DBNULL,FEATURE_DEFAULT_PARAMETER_VALUE,FEATURE_GET_TYPE_INFO,FEATURE_VARIANCE,FEATURE_SERIALIZATION,CLR45 \
        -d:MONO_INTERPRETER \
@@ -12,7 +12,9 @@ LIB_MCS_FLAGS = \
 
 ifdef MOBILE_STATIC
 mono_dynamic_interpreter_deps = $(the_libdir_base)plaincore/System.Core.dll
-LIB_MCS_FLAGS += -lib:$(the_libdir_base)plaincore
+LIB_REFS += plaincore/System.Core
+else
+LIB_REFS += System.Core
 endif
 
 include ../../build/library.make
index d52144b2154268ec3c8b3322bd9816967b29b33e..f3801411afa27024cb3d2cb3624f384c2d951fa8 100644 (file)
@@ -4,8 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Mono.Http.dll
 LIB_REFS = System System.Xml System.Web ICSharpCode.SharpZipLib Mono.Security
-LIB_MCS_FLAGS = -r:$(corlib) \
-               -nowarn:618
+LIB_MCS_FLAGS = -nowarn:618
 
 NO_TEST = yes
 
index c4a97a86a898fc9bd75931f24356566facc105f3..5b7c92c5e4d83a7d3474efdee4fac9bf7e0722e9 100644 (file)
@@ -5,7 +5,7 @@ include ../../build/rules.make
 LIBRARY = Mono.Management.dll
 
 LIB_REFS = System Mono.Posix
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index d07fee59e7e9e17fe03a716395fe8728ee7aec4c..67f382812d8c76d0d99be3a27a3070dd84cd578e 100644 (file)
@@ -6,8 +6,8 @@ LIBRARY = Mono.Messaging.RabbitMQ.dll
 LIB_REFS = System System.Messaging Mono.Messaging RabbitMQ.Client
 LIB_MCS_FLAGS = -nowarn:618
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169 \
-       /r:nunit.mocks.dll
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
+TEST_LIB_REFS = nunit.mocks
 
 include ../../build/library.make
 
index a2e3fbf7b44c30cd95a8f1e5c5f9aa3048a314f6..7788dfb60c89ec9946a89124b1f377312d4edd94 100644 (file)
@@ -7,6 +7,7 @@ LIBRARY = Mono.Messaging.dll
 LIB_REFS = System System.Configuration
 LIB_MCS_FLAGS =
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169 /r:System.Messaging.dll /r:nunit.mocks.dll
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
+TEST_LIB_REFS = System.Messaging nunit.mocks
 
 include ../../build/library.make
index beee719c77f79c11e661f5b6f74856321a674e55..2fb4724b28123360a10f265cb35ae4fe5ce77153 100644 (file)
@@ -8,8 +8,9 @@ LIBRARY_PACKAGE = none
 NO_INSTALL = yes
 
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib)
-TEST_MCS_FLAGS = /r:Mono.Posix.dll /r:System.dll /r:System.Core.dll
+LIB_MCS_FLAGS =
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = Mono.Posix System System.Core
 
 mono_sourcelibs_DIR  = $(DESTDIR)$(mono_libdir)/mono-source-libs
 mono_options_DATA = Mono.Options/Options.cs
index 23ee99324e85eb9dbcd3c37be7d7c63f4c6857dd..05810c39481db0174ff22f0c42d2954b5b044195 100644 (file)
@@ -477,7 +477,10 @@ namespace Mono.Options
                        try {
                                if (value != null) {
 #if PCL
-                                       t = (T) Convert.ChangeType (value, targetType);
+                                       if (targetType.GetTypeInfo ().IsEnum)
+                                               t = (T) Enum.Parse (targetType, value, true);
+                                       else
+                                               t = (T) Convert.ChangeType (value, targetType);
 #else
                                        TypeConverter conv = TypeDescriptor.GetConverter (targetType);
                                        t = (T) conv.ConvertFromString (value);
index a66f278498940c738b2202433d589db2f4c798f0..572223ebd667110f30f7aa6dd013693c351b4180 100644 (file)
@@ -269,6 +269,26 @@ namespace MonoTests.Mono.Options
                                        p, v => { v.Parse (_("-n=")); });
                }
 
+               [Test]
+               public void EnumValues ()
+               {
+                       DayOfWeek a = 0;
+                       OptionSet p = new OptionSet () {
+                               { "a=", (DayOfWeek v) => a = v },
+                       };
+                       p.Parse (_ ("-a=Monday"));
+                       Assert.AreEqual (a, DayOfWeek.Monday);
+                       p.Parse (_ ("-a=tuesday"));
+                       Assert.AreEqual (a, DayOfWeek.Tuesday);
+                       p.Parse (_ ("-a=3"));
+                       Assert.AreEqual (a, DayOfWeek.Wednesday);
+                       p.Parse (_ ("-a=Monday,Tuesday"));
+                       Assert.AreEqual (a, DayOfWeek.Monday | DayOfWeek.Tuesday);
+                       Utils.AssertException (typeof (OptionException),
+                                       "Could not convert string `Noday' to type DayOfWeek for option `-a'.",
+                                       p, v => { v.Parse (_ ("-a=Noday")); });
+               }
+
                [Test]
                public void BooleanValues ()
                {
index e2f587ed5e6b7ece3c9dcc9aaade968855c36736..75b5aff640be5ba18b2bd66e09a27292166e1f0e 100644 (file)
@@ -6,7 +6,8 @@ LIBRARY = Mono.Parallel.dll
 
 include ../../build/library.make
 
-TEST_MCS_FLAGS = /r:System.Core.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Core
 
 LIB_REFS += System.Core System
-LIB_MCS_FLAGS += -d:INSIDE_MONO_PARALLEL -r:$(corlib)
+LIB_MCS_FLAGS += -d:INSIDE_MONO_PARALLEL
index 9cde3498e4d17dde9a74721a7ad9a25052da0ec4..10d14fc45edf0aee2674b538db53dcf7fefb8274 100644 (file)
@@ -6,8 +6,9 @@ LIBRARY = Mono.Posix.dll
 # Don't warn about [Obsolete] members, as there are now *lots* of [Obsolete]
 # members, generating volumes of output.
 LIB_REFS = System
-LIB_MCS_FLAGS = /unsafe /r:$(corlib) /nowarn:0618,612
-TEST_MCS_FLAGS = /unsafe /r:Mono.Posix.dll /r:System.dll /nowarn:0219,0618
+LIB_MCS_FLAGS = /unsafe /nowarn:0618,612
+TEST_MCS_FLAGS = /unsafe /nowarn:0219,0618
+TEST_LIB_REFS = Mono.Posix System
 
 LIBRARY_COMPILE = $(BOOT_COMPILE)
 
index a5f641229e46c52357d9af322f91e043b5f52272..54270bccc55d7dba50f4b2fb1d7cc47860e41135 100644 (file)
@@ -3,8 +3,8 @@ SUBDIRS =
 include ../../build/rules.make
 
 LIBRARY = Mono.Security.Providers.NewTls.dll
-LIB_MCS_FLAGS = -unsafe -nowarn:1030 -keyfile:../mono.pub -delaysign -r:System.dll \
-       -r:NewSystemSource=Mono.Security.Providers.NewSystemSource.dll -r:Mono.Security.dll
+LIB_REFS = System NewSystemSource=Mono.Security.Providers.NewSystemSource Mono.Security
+LIB_MCS_FLAGS = -unsafe -nowarn:1030 -keyfile:../mono.pub -delaysign
 
 include ../../build/library.make
 
index 55e17aad73d7012b058a7295e29c9a4e050974f4..b5bf191148e12eb7995fa6f6b1ebbddc328ce77e 100644 (file)
@@ -70,3 +70,4 @@ using System.Runtime.InteropServices;
 [assembly: InternalsVisibleTo ("Mono.Security.Providers.OldTls, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
 [assembly: InternalsVisibleTo ("Mono.Security.Providers.DotNet, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
 [assembly: InternalsVisibleTo ("Mono.Security.Providers.NewSystemSource, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
+[assembly: InternalsVisibleTo ("Xamarin.BoringTls, PublicKey=002400000480000094000000060200000024000052534131000400001100000099dd12eda85767ae6f06023ee28e711c7e5a212462095c83868c29db75eddf6d8e296e03824c14fedd5f55553fed0b6173be3cc985a4b7f9fb7c83ccff8ba3938563b3d1f45a81122f12a1bcb73edcaad61a8456c7595a6da5184b4dd9d10f011b949ef1391fccfeab1ba62aa51c267ef8bd57ef1b6ba5a4c515d0badb81a78f")]
index d0e7294f80f06e2087f936e029f71a4711d9988b..6d62eca583d7d32776d05e4ac5d33e1458cd8500 100644 (file)
@@ -3,11 +3,24 @@ SUBDIRS =
 include ../../build/rules.make
 
 LIBRARY = Mono.Security.dll
-LOCAL_MCS_FLAGS = -lib:$(the_libdir_base)bare
-LIB_REFS = System
+LOCAL_MCS_FLAGS =
+LIB_REFS = bare/System
 LIB_MCS_FLAGS = -unsafe -nowarn:1030,3009
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:169,219,618,672
 
+CC_PROFILE := $(filter monotouch% xammac, $(PROFILE))
+ifdef CC_PROFILE
+
+BUILT_SOURCES = \
+       ../corlib/CommonCrypto/SHA224Managed.g.cs \
+       ../corlib/CommonCrypto/MD2Managed.g.cs \
+       ../corlib/CommonCrypto/MD4Managed.g.cs
+
+../corlib/CommonCrypto/%.g.cs:
+       $(MAKE) -C ../corlib/CommonCrypto
+
+endif
+
 include ../../build/library.make
 
 $(build_lib): $(the_libdir_base)bare/System.dll
@@ -21,5 +34,5 @@ EXTRA_DISTFILES = Mono.Security.Interface/README.md
 
 #
 # Update this comment to trigger a build in System
-# +2
+# +3
 #
index 1efcec91abde0a83b6cbc5f89caae1111a368937..bca6803ee34542a6c568a0aa5bcfe2d0e3560807 100644 (file)
@@ -205,6 +205,18 @@ namespace Mono.Security.Authenticode {
                                        ha = SHA1.Create ();
                                        hash = GetHash (ha);
                                        break;
+                               case 32:
+                                       ha = SHA256.Create ();
+                                       hash = GetHash (ha);
+                                       break;
+                               case 48:
+                                       ha = SHA384.Create ();
+                                       hash = GetHash (ha);
+                                       break;
+                               case 64:
+                                       ha = SHA512.Create ();
+                                       hash = GetHash (ha);
+                                       break;
                                default:
                                        reason = 5;
                                        Close ();
@@ -402,6 +414,15 @@ namespace Mono.Security.Authenticode {
                                case 20:
                                        hashName = "SHA1";
                                        break;
+                               case 32:
+                                       hashName = "SHA256";
+                                       break;
+                               case 48:
+                                       hashName = "SHA384";
+                                       break;
+                               case 64:
+                                       hashName = "SHA512";
+                                       break;
                        }
                        HashAlgorithm ha = HashAlgorithm.Create (hashName);
                        if (!messageDigest.CompareValue (ha.ComputeHash (signature)))
index 13f0f5d8e65a639248892d5cedd5011cd4dd6aac..a428e0624b1ec82cef0e4912ff8e93588ca0aa5a 100644 (file)
@@ -27,6 +27,8 @@
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 
+#if !MONOTOUCH && !XAMMAC
+
 using System;
 
 namespace Mono.Security.Cryptography { 
@@ -195,3 +197,5 @@ namespace Mono.Security.Cryptography {
                }
        }
 }
+
+#endif
\ No newline at end of file
index eedc8b114b195cc46aa29415cbec47f46aea298f..adbd7fb876b841c88f77e7947e9ad8e158cfaba2 100644 (file)
@@ -27,6 +27,8 @@
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 
+#if !MONOTOUCH && !XAMMAC
+
 using System;
 
 namespace Mono.Security.Cryptography { 
@@ -282,3 +284,5 @@ namespace Mono.Security.Cryptography {
                }
        }
 }
+
+#endif
\ No newline at end of file
index 88d4fe59955af86f654d2a5f8ce3093d10720a63..a0da4344b9524c0d1e02264f88c828cd53b283ef 100644 (file)
@@ -29,6 +29,8 @@
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 
+#if !MONOTOUCH && !XAMMAC
+
 using System.Security.Cryptography;
 
 namespace Mono.Security.Cryptography {
@@ -256,3 +258,4 @@ namespace Mono.Security.Cryptography {
        }
 }
 
+#endif
\ No newline at end of file
index fc901084a7033bd84d08cd41e36590e0e52179b8..fd392b409e5a4bef6de68f174911b79f638997be 100644 (file)
@@ -95,6 +95,14 @@ namespace Mono.Security.Interface
                 * If @serverMode is true, then we're a server and want to validate a certificate that we received from a client.
                 */
                ValidationResult ValidateCertificate (string targetHost, bool serverMode, X509CertificateCollection certificates);
+       }
+
+       internal interface ICertificateValidator2 : ICertificateValidator
+       {
+               /*
+                * Internal use only.
+                */
+               ValidationResult ValidateCertificate (string targetHost, bool serverMode, X509Certificate leaf, X509Chain chain);
 
                /*
                 * On OS X and Mobile, the @chain will be initialized with the @certificates, but not actually built.
@@ -137,25 +145,20 @@ namespace Mono.Security.Interface
                        get { return supportsTrustAnchors; }
                }
 
-               static ICertificateValidator GetDefaultValidator (MonoTlsProvider provider, MonoTlsSettings settings)
-               {
-                       return (ICertificateValidator)NoReflectionHelper.GetDefaultCertificateValidator (provider, settings);
-               }
-
                /*
                 * Internal API, intended to be used by MonoTlsProvider implementations.
                 */
-               public static ICertificateValidator GetValidator (MonoTlsProvider provider, MonoTlsSettings settings)
+               internal static ICertificateValidator2 GetDefaultValidator (MonoTlsSettings settings, MonoTlsProvider provider)
                {
-                       return GetDefaultValidator (provider, settings);
+                       return (ICertificateValidator2)NoReflectionHelper.GetDefaultCertificateValidator (provider, settings);
                }
 
                /*
                 * Use this overloaded version in user code.
                 */
-               public static ICertificateValidator GetValidator (MonoTlsSettings settings)
+               public static ICertificateValidator GetValidator (MonoTlsSettings settings, MonoTlsProvider provider = null)
                {
-                       return GetDefaultValidator (null, settings);
+                       return GetDefaultValidator (settings, provider);
                }
        }
 }
index 753cd97e5a23952166c2f74f6effd7524a407c6d..089d8447a78993d3a4015cf4ad40b6a47cb6f6ed 100644 (file)
@@ -124,12 +124,32 @@ namespace Mono.Security.Interface
 
 #endregion
 
+#region Native Certificate Implementation
+
+               internal virtual bool HasNativeCertificates {
+                       get { return false; }
+               }
+
+               internal virtual X509Certificate2Impl GetNativeCertificate (
+                       byte[] data, string password, X509KeyStorageFlags flags)
+               {
+                       throw new InvalidOperationException ();
+               }
+
+               internal virtual X509Certificate2Impl GetNativeCertificate (
+                       X509Certificate certificate)
+               {
+                       throw new InvalidOperationException ();
+               }
+
+#endregion
+
 #region Certificate Validation
 
                /*
                 * Allows a TLS provider to provide a custom system certificiate validator.
                 */
-               public virtual bool HasCustomSystemCertificateValidator {
+               internal virtual bool HasCustomSystemCertificateValidator {
                        get { return false; }
                }
 
@@ -142,13 +162,12 @@ namespace Mono.Security.Interface
                 * Returns `true` if certificate validation has been performed and `false` to invoke the
                 * default system validator.
                 */
-               public virtual bool InvokeSystemCertificateValidator (
-                       ICertificateValidator validator, string targetHost, bool serverMode,
-                       X509CertificateCollection certificates, X509Chain chain, out bool success,
-                       ref MonoSslPolicyErrors errors, ref int status11)
+               internal virtual bool InvokeSystemCertificateValidator (
+                       ICertificateValidator2 validator, string targetHost, bool serverMode,
+                       X509CertificateCollection certificates, bool wantsChain, ref X509Chain chain,
+                       out bool success, ref MonoSslPolicyErrors errors, ref int status11)
                {
-                       success = false;
-                       return false;
+                       throw new InvalidOperationException ();
                }
 
 #endregion
index 513dc61bd4fdea8fdd3c87a8df120f01c13ccd9d..36918de7763e9ed1c24609f0a67e752c39967081 100644 (file)
@@ -1 +1,3 @@
 #include mobile_Mono.Security.dll.sources
+../corlib/CommonCrypto/CommonCrypto.cs
+../corlib/CommonCrypto/RC4CommonCrypto.cs
diff --git a/mcs/class/Mono.Security/monotouch_opt_Mono.Security.dll.sources b/mcs/class/Mono.Security/monotouch_opt_Mono.Security.dll.sources
deleted file mode 100644 (file)
index e8464be..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-./Mono.Security.Cryptography/ARC4Managed.cs
-./Mono.Security.Cryptography/MD2Managed.cs
-./Mono.Security.Cryptography/MD4Managed.cs
-./Mono.Security.Cryptography/SHA224Managed.cs
diff --git a/mcs/class/Mono.Security/monotouch_tv_opt_Mono.Security.dll.sources b/mcs/class/Mono.Security/monotouch_tv_opt_Mono.Security.dll.sources
deleted file mode 100644 (file)
index 19d6a04..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_Mono.Security.dll.sources
diff --git a/mcs/class/Mono.Security/monotouch_watch_opt_Mono.Security.dll.sources b/mcs/class/Mono.Security/monotouch_watch_opt_Mono.Security.dll.sources
deleted file mode 100644 (file)
index 19d6a04..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_Mono.Security.dll.sources
index 1379fa79d8038df905a3a62f2e9bf124b648466d..698996a1d709c630c585a43f2f5ac90021c5e65a 100644 (file)
@@ -1,2 +1,4 @@
 #include monotouch_Mono.Security.dll.sources
+../corlib/CommonCrypto/CommonCrypto.cs
+../corlib/CommonCrypto/RC4CommonCrypto.cs
 
diff --git a/mcs/class/Mono.Security/xammac_opt_Mono.Security.dll.sources b/mcs/class/Mono.Security/xammac_opt_Mono.Security.dll.sources
deleted file mode 100644 (file)
index e8464be..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-./Mono.Security.Cryptography/ARC4Managed.cs
-./Mono.Security.Cryptography/MD2Managed.cs
-./Mono.Security.Cryptography/MD4Managed.cs
-./Mono.Security.Cryptography/SHA224Managed.cs
index 3e394f9287d9844f3ccad7606f3d0bfaed7988a9..d8e1e47414107bd6f95da97b4d1cf223d9f810cd 100644 (file)
@@ -4,8 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = Mono.Simd.dll
 LIB_REFS = System.Core
-LIB_MCS_FLAGS = -r:$(corlib) /unsafe
-TEST_MCS_FLAGS = -r:Mono.Simd.dll
+LIB_MCS_FLAGS = /unsafe
 
 NO_TEST = yes
 
index 8aabd350f40cef794cef17ee3bcfe2c8b01fd9a1..0e2a01190908f45ca20d357485ac7db8c67c57d8 100755 (executable)
@@ -6,20 +6,7 @@
 #
 # Copyright (c) 2007 Novell, Inc.
 #
-# This program is free software; you can redistribute it and/or
-# modify it under the terms of version 2 of the GNU General Public
-# License as published by the Free Software Foundation.
-#
-# 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., 59 Temple Place - Suite 330,
-# Boston, MA 02111-1307, USA.
-##############################################################
+# Licensed under the MIT license. See LICENSE file in the project root for full license information.
 
 
 
index ef144fe461de5ddc869c9b340e9a8296300434e3..8d50c7ad6294d7f8c10c527a4b39005e1c272e01 100644 (file)
@@ -7,11 +7,8 @@ include $(XBUILD_DIR)/xbuild.make
 
 LIBRARY = Mono.XBuild.Tasks.dll
 
-LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = \
-       /r:$(corlib)                            \
-       /r:System.dll                           \
-       /r:System.Xml.dll
+LIB_REFS = $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Xml
+LIB_MCS_FLAGS =
 
 include $(XBUILD_DIR)/xbuild_test.make
 
index 32b46e6664a290d399701de9d9f919500afe9035..e7ac06790fb53969ee5264f120f45abf95affe33 100644 (file)
@@ -11,7 +11,7 @@ SCARY_LIB=/lib:$(prefix)/lib
 endif
 
 LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = $(SCARY_LIB) /unsafe /r:$(corlib)
+LIB_MCS_FLAGS = $(SCARY_LIB) /unsafe
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
 
 EXTRA_DISTFILES = \
index 25cd6cc4fdc4610fb6a4783f4cc441acf6f8e44a..9e0d99d6c0b7de775b2ecfc44b3d2a0067d41f15 100644 (file)
@@ -7,9 +7,6 @@ LIBRARY = Novell.Directory.Ldap.dll
 LIB_REFS = System Mono.Security
 LIB_MCS_FLAGS = \
        -warn:1 -nowarn:612 \
-       -r:$(corlib)                            \
-       -r:System.dll                           \
-       -r:Mono.Security.dll                    \
        $(RESX_RES:%=/res:%)
 
 include ../../build/library.make
index e699f77f53f1f88d963a7d07db05b820b682066a..f303415ba6ddae5b83ededf702d4c221c01dd489 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = PEAPI.dll
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib) -nowarn:414,618
+LIB_MCS_FLAGS = -nowarn:414,618
 NO_TEST = yes
 
 EXTRA_DISTFILES = README.txt
diff --git a/mcs/class/RabbitMQ.Client/Makefile.orig b/mcs/class/RabbitMQ.Client/Makefile.orig
deleted file mode 100644 (file)
index 84182ff..0000000
+++ /dev/null
@@ -1,64 +0,0 @@
-NAME=rabbitmq-dotnet-client
-NAME_VSN=${NAME}-${RABBIT_VSN}
-
-RELEASE_DIR=releases/${NAME}/v${RABBIT_VSN}
-
-STAGE_RELEASE_DIR=charlotte:/home/rabbitmq/stage-extras/releases/${NAME}
-LIVE_RELEASE_DIR=charlotte:/home/rabbitmq/live-extras/releases/${NAME}
-
-RSYNC_CMD=rsync -irvl --delete-after
-
-TMPXMLZIP=${NAME_VSN}-tmp-xmldoc.zip
-
-ifeq "$(RABBIT_VSN)" ""
-rabbit-vsn:
-       @echo "RABBIT_VSN is not set"
-       @false
-else
-rabbit-vsn: 
-endif
-
-deploy-stage: rabbit-vsn ensure-deliverables
-       ${RSYNC_CMD} --exclude=${TMPXMLZIP} releases/${NAME}/ ${STAGE_RELEASE_DIR}
-
-deploy-live: rabbit-vsn ensure-deliverables
-       ${RSYNC_CMD} --exclude=${TMPXMLZIP} releases/${NAME}/ ${LIVE_RELEASE_DIR}
-
-ensure-deliverables: rabbit-vsn
-       file ${RELEASE_DIR}/${NAME_VSN}.zip
-       file ${RELEASE_DIR}/${NAME_VSN}-api-guide.pdf
-       file ${RELEASE_DIR}/${NAME_VSN}-user-guide.pdf
-       file ${RELEASE_DIR}/${NAME_VSN}-wcf-service-model.pdf
-       file ${RELEASE_DIR}/${NAME_VSN}-net-2.0.zip
-       file ${RELEASE_DIR}/${NAME_VSN}-net-2.0-htmldoc.zip
-       file ${RELEASE_DIR}/${NAME_VSN}-net-2.0-htmldoc
-       file ${RELEASE_DIR}/${NAME_VSN}-net-3.0-wcf.zip
-       file ${RELEASE_DIR}/${NAME_VSN}-net-3.0-wcf-htmldoc.zip
-       file ${RELEASE_DIR}/${NAME_VSN}-net-3.0-wcf-htmldoc
-
-ensure-prerequisites: rabbit-vsn
-       dpkg -p htmldoc plotutils transfig graphviz > /dev/null
-
-ensure-release-dir: rabbit-vsn
-       touch ${RELEASE_DIR}/
-
-ensure-docs: rabbit-vsn
-       file ${RELEASE_DIR}/${NAME_VSN}-net-2.0-htmldoc.zip
-       file ${RELEASE_DIR}/${TMPXMLZIP}
-
-doc: rabbit-vsn ensure-prerequisites ensure-release-dir ensure-docs
-       rm -rf build/tmpdoc build/doc
-       mkdir -p build/tmpdoc/html build/tmpdoc/xml
-       unzip -j ${RELEASE_DIR}/${NAME_VSN}-net-2.0-htmldoc.zip -d build/tmpdoc/html
-       unzip -j ${RELEASE_DIR}/${NAME_VSN}-tmp-xmldoc.zip -d build/tmpdoc/xml
-       cd docs && ./api-guide.sh && \
-         mv api-guide.pdf ../${RELEASE_DIR}/${NAME_VSN}-api-guide.pdf
-       $(MAKE) -C docs
-       mv build/doc/userguide/user-guide.pdf ${RELEASE_DIR}/${NAME_VSN}-user-guide.pdf
-       cp docs/"RabbitMQ Service Model.pdf" \
-         ${RELEASE_DIR}/${NAME_VSN}-wcf-service-model.pdf
-       cd ${RELEASE_DIR} && \
-         rm -rf ${NAME_VSN}-net-2.0-htmldoc && \
-         unzip ${NAME_VSN}-net-2.0-htmldoc.zip && \
-         rm -rf unzip ${NAME_VSN}-net-3.0-wcf-htmldoc && \
-         unzip ${NAME_VSN}-net-3.0-wcf-htmldoc.zip
index 9d5e49a318156426af592e19ce0c9142f98f731c..9c48a40e29ddfb28882d65f65c684f91a69122ea 100644 (file)
@@ -4,9 +4,7 @@ SUBDIRS =
 include ../../../../build/rules.make
 
 PROGRAM = RabbitMQ.Client.Apigen.exe
-
-LOCAL_MCS_FLAGS = /r:System.dll     \
-                  /r:System.Xml.dll \
-                  /main:RabbitMQ.Client.Apigen.Apigen
+LIB_REFS = System System.Xml
+LOCAL_MCS_FLAGS = /main:RabbitMQ.Client.Apigen.Apigen
 
 include ../../../../build/executable.make
index 2da44f09fe567c5cae5d4d53fe703c7810e4b88e..cc8b4f8e95c096df78e66cd908d2ec93d242a37a 100644 (file)
@@ -3,7 +3,7 @@ include ../../build/rules.make
 
 LIBRARY = System.Configuration.Install.dll
 LIB_REFS = System System.Xml
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 
 NO_TEST = yes
 
index 43fc4253383bc9b14704a56345d09e916ff320a4..5815830b6b9f18d4010a81939caa006ba5bd1585 100644 (file)
@@ -5,11 +5,11 @@ include ../../build/rules.make
 
 LIBRARY = System.Configuration.dll
 
-LOCAL_MCS_FLAGS = -lib:$(secxml_libdir) -lib:$(bare_libdir)
-test_remove = $(LOCAL_MCS_FLAGS)
-LIB_REFS = System System.Xml System.Security
-LIB_MCS_FLAGS = -r:$(corlib) -nowarn:618
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) 
+LOCAL_MCS_FLAGS = 
+LIB_REFS = secxml/System bare/System.Xml System.Security
+LIB_MCS_FLAGS = -nowarn:618
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Xml System
 
 include ../../build/library.make
 
@@ -31,3 +31,6 @@ $(the_libdir_base)System.Security.dll:
 
 $(bare_libdir)/System.Xml.dll:
        (cd ../System.XML; $(MAKE) $@)
+
+run-test:
+       $(MAKE) -C Test/standalone
\ No newline at end of file
index e4d59f1466c2c3ba5604f17d5af8443d41d7afe9..0cf6136ae38ca111de4ffb463a475245dd7cf4b0 100644 (file)
@@ -69,6 +69,11 @@ namespace System.Configuration
                public virtual Type GetConfigType (string typeName, bool throwOnError)
                {
                        Type type = Type.GetType (typeName);
+
+                       // This code is in System.Configuration.dll, but some of the classes we might want to load here are in System.dll.
+                       if (type == null)
+                               type = Type.GetType (typeName + ",System");
+
                        if (type == null && throwOnError)
                                throw new ConfigurationErrorsException ("Type '" + typeName + "' not found.");
                        return type;
index 3a1a8a84e32c7b9c78af2e66e67e9b9541ff81e0..b203b7b9099cdafa132d38778fd1d2ce7b4a8fcb 100644 (file)
@@ -1,30 +1,37 @@
-TESTS = t1.exe t2.exe t3.exe t4.exe t5.exe t6.exe t7.exe t8.exe t9.exe t10.exe t11.exe t12.exe t15.exe t16.exe t17.exe t18.exe t19.exe t20.exe t21.exe t22.exe t23.exe t24.exe t25.exe t26.exe t27.exe t28.exe t29.exe t30.exe t31.exe t32.exe t33.exe t34.exe t35.exe t36.exe t37.exe t38.exe t39.exe t40.exe t41.exe t42.exe t43.exe t44.exe t45.exe t46.exe t47.exe
-# t13.exe t14.exe
+thisdir = class/System.Configuration/Test/standalone
+SUBDIRS = 
+include ../../../../build/rules.make
+
+TESTS = t1.exe t2.exe t3.exe t4.exe t5.exe t6.exe t7.exe t8.exe t9.exe t10.exe t11.exe t12.exe t15.exe t16.exe t17.exe t18.exe t19.exe t20.exe t21.exe t22.exe t23.exe t24.exe t25.exe t28.exe t29.exe t30.exe t31.exe t32.exe t33.exe t34.exe t35.exe t36.exe t37.exe t38.exe t39.exe t40.exe t41.exe t42.exe t43.exe t44.exe t45.exe t46.exe t47.exe t48.exe
+# t13.exe t14.exe t26.exe t27.exe
 
 check: local compare
 
 local: $(TESTS)
        @for i in $(TESTS); do \
                echo running test $$i; \
-               MONO_PATH=../../../lib/net_4_x mono --debug $$i > $$i.result; \
+               MONO_PATH="$(topdir)/class/lib/$(PROFILE)$(PLATFORM_PATH_SEPARATOR)$$MONO_PATH" $(RUNTIME) $(RUNTIME_FLAGS) $$i > $$i.result; \
        done
 
 compare:
-       @for i in $(TESTS); do \
-               echo -n "$$i: "; \
-               if diff --strip-trailing-cr $$i.expected $$i.result >/dev/null ; then echo "  OK"; else echo "  FAILED"; fi; \
-       done
+       @ECODE=0; \
+       for i in $(TESTS); do \
+               printf "$$i: "; \
+               if diff --strip-trailing-cr $$i.expected $$i.result >/dev/null ; then echo "  OK"; else echo "  FAILED"; ECODE=1; fi; \
+       done; \
+       exit $$ECODE
 
 clean:
        rm -f *.exe *.mdb *.result
 
 t36.exe : t36.cs t36-lib.cs
-       gmcs /debug -r:System.Configuration.dll -t:library t36-lib.cs
-       gmcs /debug -r:System.Configuration.dll -r:t36-lib.dll t36.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Configuration.dll -t:library t36-lib.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Configuration.dll -r:t36-lib.dll t36.cs
 
 t46.exe : t46.cs t46-lib.cs
-       gmcs /debug -r:System.Configuration.dll -t:library t46-lib.cs
-       gmcs /debug -r:System.Configuration.dll -r:t46-lib.dll /out:$@ Assert.cs t46.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Configuration.dll -t:library t46-lib.cs
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/System.Configuration.dll -r:t46-lib.dll /out:$@ Assert.cs t46.cs
 
 %.exe: %.cs
-       gmcs /debug /out:$@ Assert.cs $< -r:System.Configuration.dll -r:System.Web.dll -r:System.Data.dll
+       $(CSCOMPILE) /out:$@ Assert.cs $< -r:$(topdir)/class/lib/$(PROFILE)/System.Configuration.dll -r:$(topdir)/class/lib/$(PROFILE)/System.Web.dll -r:$(topdir)/class/lib/$(PROFILE)/System.Data.dll -r:$(topdir)/class/lib/$(PROFILE)/System.dll -r:$(topdir)/class/lib/$(PROFILE)/System.Xml.dll
+
diff --git a/mcs/class/System.Configuration/Test/standalone/t48.cs b/mcs/class/System.Configuration/Test/standalone/t48.cs
new file mode 100644 (file)
index 0000000..6d7bc05
--- /dev/null
@@ -0,0 +1,24 @@
+using System;
+using System.Collections;
+
+// Bugzilla #39669
+
+namespace TestConfigSection
+{
+       class Test
+       {
+               public static int Main (string[] args)
+               {
+                       Hashtable testCustomSection = (Hashtable)System.Configuration.ConfigurationManager.GetSection ("TestCustomSection");
+                       string proxyServer = (string)testCustomSection["ProxyServer"];
+
+                       if (proxyServer == null)
+                               throw new Exception("Custom section value is null");
+
+                       if (proxyServer != "server.example.com")
+                               throw new Exception("Custom section value is incorrect");
+
+                       return 0;
+               }
+       }
+}
diff --git a/mcs/class/System.Configuration/Test/standalone/t48.exe.config b/mcs/class/System.Configuration/Test/standalone/t48.exe.config
new file mode 100644 (file)
index 0000000..ebdf8a8
--- /dev/null
@@ -0,0 +1,10 @@
+<?xml version="1.0" encoding="utf-8"?>
+<configuration>
+  <configSections>
+    <section name="TestCustomSection" type="System.Configuration.DictionarySectionHandler" />
+  </configSections>
+  <TestCustomSection>
+    <add key="ProxyServer" value="server.example.com" />
+    <add key="ConnectOnStart" value="false" />
+  </TestCustomSection>
+</configuration>
\ No newline at end of file
diff --git a/mcs/class/System.Configuration/Test/standalone/t48.exe.expected b/mcs/class/System.Configuration/Test/standalone/t48.exe.expected
new file mode 100644 (file)
index 0000000..e69de29
index 716df15e60aaece8709997745707c2b63e8a9672..60fcec9fb7628639b1fe964ea084d3a1a1830060 100644 (file)
@@ -47,6 +47,16 @@ ifdef CLR_PROFILE
 LIB_REFS += Mono.Posix
 endif
 
+CC_PROFILE := $(filter monotouch% xammac, $(PROFILE))
+ifdef CC_PROFILE
+BUILT_SOURCES = \
+       ../corlib/CommonCrypto/AesManaged.g.cs \
+       ../corlib/CommonCrypto/AesCryptoServiceProvider.g.cs
+
+../corlib/CommonCrypto/%.g.cs:
+       $(MAKE) -C ../corlib/CommonCrypto
+endif
+
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
 
 include ../../build/library.make
index 7d32d44a88bd84c6036228fd2caebd01a9efbf7b..b050f33be704a921beae2be322fe8df90b6b0afe 100644 (file)
@@ -1,2 +1 @@
-#include common_System.Core.dll.sources
-#include interpreter_System.Core.dll.sources
+#include monotouch_System.Core.dll.sources
index 7d32d44a88bd84c6036228fd2caebd01a9efbf7b..b050f33be704a921beae2be322fe8df90b6b0afe 100644 (file)
@@ -1,2 +1 @@
-#include common_System.Core.dll.sources
-#include interpreter_System.Core.dll.sources
+#include monotouch_System.Core.dll.sources
index 882476b4b5e7308adf7bb8013f2c75a43f6c2d46..ffee84a901d63aa9ce622a669154efd6bc8560e3 100644 (file)
@@ -1,4 +1,3 @@
 #include common_System.Core.dll.sources
 
 #include dynamic_System.Core.dll.sources
-
index a4415a382bd4bce358826b9cd00e9c5e8bed9c39..2a70299375e2d0b0945dab6dde31376765b61d0b 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = System.Data.OracleClient.dll
 LIB_REFS = System System.Xml System.Data System.EnterpriseServices System.Drawing
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) /nowarn:618
 
index e0af49f576e0178654e470b213f8688a198a0e94..6ff30b0bc856cceeeed5a815b549e2e76f1f6664 100644 (file)
@@ -964,7 +964,7 @@ namespace System.Data.OracleClient
                {
                        OracleCommand cmd = CreateCommand ();
 
-                       cmd.CommandText = "SSELECT OWNER, OBJECT_NAME, SUBOBJECT_NAME, OBJECT_ID, DATA_OBJECT_ID, LAST_DDL_TIME, " +
+                       cmd.CommandText = "SELECT OWNER, OBJECT_NAME, SUBOBJECT_NAME, OBJECT_ID, DATA_OBJECT_ID, LAST_DDL_TIME, " +
                                "    TIMESTAMP, STATUS, TEMPORARY, GENERATED, SECONDARY, CREATED " +
                                " FROM ALL_OBJECTS " +
                                " WHERE OBJECT_TYPE = '" + objType + "' " +
index 5f9aeccafce598da00344ce165221e47a8a90874..b5fb3cb6fdd43622e5dcbd4664aa43b53329969f 100644 (file)
@@ -11,6 +11,7 @@ ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
 LIB_REFS += System.ServiceModel.Activation
 endif
 
-TEST_MCS_FLAGS = -r:System.ServiceModel.dll -r:System.Core.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.ServiceModel System.Core
 
 include ../../build/library.make
index 9e19d39aed4c00ec15fedb482998a69ce3067e8c..0c84bbb1b4596a37674c746cdd4467ff84417034 100644 (file)
@@ -28,7 +28,8 @@ endif
 
 TXT_RESOURCE_STRINGS = ../../../external/referencesource/System.Data/system.data.txt
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -r:System.Core.dll -r:Mono.Data.Sqlite.dll -nowarn:618,169,612,219,168
+TEST_LIB_REFS = System.Core Mono.Data.Sqlite
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:618,169,612,219,168
 
 TEST_MONO_PATH = .
 
diff --git a/mcs/class/System.Deployment/Assembly/AssemblyInfo.cs b/mcs/class/System.Deployment/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..460e662
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Deployment.dll")]
+[assembly: AssemblyDescription ("System.Deployment.dll")]
+[assembly: AssemblyDefaultAlias ("System.Deployment.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Deployment/Makefile b/mcs/class/System.Deployment/Makefile
new file mode 100644 (file)
index 0000000..87b8ba7
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Deployment
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Deployment.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../msfinal.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Deployment/System.Deployment.dll.sources b/mcs/class/System.Deployment/System.Deployment.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
index e941324ef83cafd239f80d65df847e4ff0104c26..3dc11aa3b01e293dc886b475ccd6ff36704715d2 100644 (file)
@@ -4,13 +4,11 @@ include ../../build/rules.make
 
 LIBRARY = System.Design.dll
 
-LIB_REFS = System System.Xml System.Web System.Windows.Forms System.Drawing Accessibility System.Data System.Configuration
-LIB_MCS_FLAGS = -r:$(corlib)
+LIB_REFS = System System.Xml plainweb/System.Web System.Windows.Forms System.Drawing Accessibility System.Data System.Configuration
+LIB_MCS_FLAGS =
 
-plainweb_dir = $(the_libdir_base)plainweb
-LOCAL_MCS_FLAGS = -lib:$(plainweb_dir)
-
-TEST_MCS_FLAGS = /r:System.dll -r:System.Drawing.dll -r:System.Windows.Forms
+TEST_LIB_REFS = System System.Drawing System.Windows.Forms
+TEST_MCS_FLAGS =
 
 include ../../build/library.make
 
index ff5403fd06a9fc2a583051869f7a69a85d068f78..7eccfe87a4e731d6cac7f8f7ae98709cebd1463a 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = System.DirectoryServices.dll
 LIB_REFS = System Novell.Directory.Ldap
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 
 include ../../build/library.make
index 9fa2fea63b52942595784a69c89493953f34c9da..7abb4b3f3aed433d4ad2975c59cdb8016af1414e 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = System.Drawing.Design.dll
 LIB_REFS = System System.Drawing System.Windows.Forms
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index 8827cb4f826929dbba8d2605da6f3972a634df93..59ff776b9f1ccbf1bb35ea36e60206a59417782f 100644 (file)
@@ -5,13 +5,14 @@ SUBDIRS =
 LIBRARY = System.Drawing.dll
 
 LIB_REFS = System
-LIB_MCS_FLAGS = /unsafe /r:$(corlib) \
+LIB_MCS_FLAGS = /unsafe \
        -resource:Assembly/Mono.ico,Mono.ico -resource:Assembly/Information.ico,Information.ico \
        -resource:Assembly/Error.ico,Error.ico -resource:Assembly/Warning.ico,Warning.ico \
        -resource:Assembly/Question.ico,Question.ico -resource:Assembly/Shield.ico,Shield.ico
 
+TEST_LIB_REFS = System.Drawing System.Runtime.Serialization.Formatters.Soap System.Xml
+
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -define:TEST -resource:Test/resources/indexed.png,indexed.png \
-        -r:System.Drawing.dll -r:System.Runtime.Serialization.Formatters.Soap.dll -r:System.Xml.dll \
        -nowarn:0618 -nowarn:219 -nowarn:169
 
 include ../../build/library.make
index f0eac39bcdf5cf9df7b333031f147f91d7d64ffb..90f38e9fc9ade77d12212d6d6ceffb38a063ab2d 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = System.EnterpriseServices.dll
 LIB_REFS = System.Transactions
-LIB_MCS_FLAGS = /nowarn:0168 /nowarn:0162 /r:$(corlib)
+LIB_MCS_FLAGS = /nowarn:0168 /nowarn:0162
 NO_TEST = yes
 
 include ../../build/library.make
index d8b918ebce307242c16d0e3383b39fa948badb2c..7cfa024a71de3b0be96972f3dbe6ff146e649d33 100644 (file)
@@ -5,6 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.IO.Compression.FileSystem.dll
 LIB_REFS = System System.IO.Compression
 LIB_MCS_FLAGS =
-TEST_MCS_FLAGS = /r:System /r:System.Core /r:System.IO.Compression.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Core System.IO.Compression
 
 include ../../build/library.make
index 7b2bd8144fb4fe6c7e7ad159dde706049e957825..0987f09e6e3085a0a4802b7c47a198d065cee52b 100644 (file)
@@ -5,6 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.IO.Compression.dll
 LIB_REFS = System System.Core
 LIB_MCS_FLAGS = /unsafe
-TEST_MCS_FLAGS = /r:System /r:System.Core
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Core
 
 include ../../build/library.make
index 9bf7e1d5877a04ff18d63b6b9fe8002f11023ab6..5a8a72c4c50e416866c1a7670beb50a626555741 100644 (file)
@@ -2,12 +2,6 @@ thisdir = class/System.IdentityModel
 SUBDIRS = 
 include ../../build/rules.make
 
-ifndef NO_SYSTEM_WEB_APPSERVICES_DEPENDENCY
-ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
-OTHER_LIB_MCS_FLAGS = -r:System.Web.ApplicationServices.dll
-endif
-endif
-
 LIBRARY = System.IdentityModel.dll
 LIB_REFS = System System.Xml System.Security System.Configuration Mono.Security System.Runtime.Serialization
 LIB_MCS_FLAGS = \
@@ -18,6 +12,13 @@ ifndef NO_SYSTEM_WEB_DEPENDENCY
 LIB_REFS += System.Web
 endif
 
+
+ifndef NO_SYSTEM_WEB_APPSERVICES_DEPENDENCY
+ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
+LIB_REFS += System.Web.ApplicationServices
+endif
+endif
+
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
 
 EXTRA_DISTFILES = \
index 4fe9d03dca2d1ff0808913fbdbed90c9da9de364..df76cf43bc2b085e3bc3c690db46e0ccaa0b00f2 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 LIBRARY = System.Management.dll
 LIB_REFS = System System.Configuration.Install
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 NO_TEST = yes
 
 include ../../build/library.make
index 4cf4c29ab083040b47ed92087f5c42d22d0fdd2a..0412ea01555cf6bbcf44cb375c526bc75b3406bd 100644 (file)
@@ -10,8 +10,8 @@ LIB_REFS += System.Drawing
 endif
 
 LIB_MCS_FLAGS = /resource:System.Messaging/MessageQueue.resx
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169 \
-               /r:nunit.mocks.dll
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
+TEST_LIB_REFS = nunit.mocks
 
 EXTRA_DISTFILES = System.Messaging/MessageQueue.resx
 
index fad726ff5f37fe25c837b901c5319e60293cd55f..b0d8e7a1a87879a4ee0431abe256ec6ab3538128 100644 (file)
@@ -7,6 +7,7 @@ LIBRARY = System.Net.Http.WebRequest.dll
 LIB_REFS = System.Net.Http System
 LIB_MCS_FLAGS =
 
-TEST_MCS_FLAGS = -r:System.Net.Http.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Net.Http
 
 include ../../build/library.make
diff --git a/mcs/class/System.Net.Http/CFContentStream.cs b/mcs/class/System.Net.Http/CFContentStream.cs
new file mode 100644 (file)
index 0000000..270846c
--- /dev/null
@@ -0,0 +1,133 @@
+//
+// CFContentStream.cs
+//
+// Authors:
+//     Marek Safar  <marek.safar@gmail.com>
+//
+// Copyright (C) 2013 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System.Threading;
+using System.Threading.Tasks;
+using System.IO;
+using System.Net;
+
+#if XAMCORE_4_0
+using CFNetwork;
+#elif XAMCORE_2_0
+using CoreServices;
+#else
+using MonoTouch.CoreServices;
+#endif
+
+namespace System.Net.Http
+{
+       class BufferData 
+       {
+               public byte[] Buffer;
+               public int Length;
+       }
+
+       class CFContentStream : HttpContent
+       {
+               readonly CFHTTPStream http_stream;
+               BufferData data;
+               Mutex data_mutex;
+               AutoResetEvent data_event;
+               AutoResetEvent data_read_event;
+
+               // The requirements are:
+               // * We must read at least one byte from the stream every time
+               //   we get a HasBytesAvailable event.
+               // * SerializeToStreamAsync is executed on a separate thread,
+               //   so reads must somehow be synchronized with that thread.
+               //
+               // Current implementation:
+               // * We read data in ReadStreamData (on the same thread
+               //   we got the HasBytesAvailable event, i.e. inside the 
+               //   HasBytesAvailable event handler).
+               // * Data is stored in a class-level buffer.
+               // * SerializeToStreamAsync blocks while waiting for
+               //   data from ReadStreamData.
+               // * ReadStreamData will only read more data once SerializeToStreamAsync
+               //   has consumed any existing data. This means we'll be
+               //   blocking in the HasBytesAvailable event handler until
+               //   any previously read data has been processed (this prevents
+               //   any unbound memory growth).
+
+               public CFContentStream (CFHTTPStream stream)
+               {
+                       this.http_stream = stream;
+                       data = new BufferData () {
+                               Buffer = new byte [4096],
+                       };
+                       data_event = new AutoResetEvent (false);
+                       data_read_event = new AutoResetEvent (true);
+                       data_mutex = new Mutex ();
+               }
+
+               public void ReadStreamData ()
+               {
+                       data_read_event.WaitOne (); // make sure there's no pending data.
+
+                       data_mutex.WaitOne ();
+                       data.Length = (int) http_stream.Read (data.Buffer, 0, data.Buffer.Length);
+                       data_mutex.ReleaseMutex ();
+
+                       data_event.Set ();
+               }
+
+               public void Close ()
+               {
+                       data_read_event.WaitOne (); // make sure there's no pending data
+
+                       data_mutex.WaitOne ();
+                       data = null;
+                       data_mutex.ReleaseMutex ();
+
+                       data_event.Set ();
+               }
+
+               protected internal override async Task SerializeToStreamAsync (Stream stream, TransportContext context)
+               {
+                       while (data_event.WaitOne ()) {
+                               data_mutex.WaitOne ();
+                               if (data == null || data.Length <= 0) {
+                                       data_mutex.ReleaseMutex ();
+                                       data_read_event.Set ();
+                                       break;
+                               }
+
+                               await stream.WriteAsync (data.Buffer, 0, data.Length).ConfigureAwait (false);
+                               data_mutex.ReleaseMutex ();
+
+                               data_read_event.Set ();
+                       }
+               }
+
+               protected internal override bool TryComputeLength (out long length)
+               {
+                       length = 0;
+                       return false;
+               }
+       }
+}
diff --git a/mcs/class/System.Net.Http/CFNetworkHandler.cs b/mcs/class/System.Net.Http/CFNetworkHandler.cs
new file mode 100644 (file)
index 0000000..5723acb
--- /dev/null
@@ -0,0 +1,332 @@
+//
+// CFNetworkHandler.cs
+//
+// Authors:
+//     Marek Safar  <marek.safar@gmail.com>
+//
+// Copyright (C) 2013 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System.Threading;
+using System.Net.Http.Headers;
+using System.Threading.Tasks;
+using System.IO;
+using System.Collections.Generic;
+using System.Net;
+
+#if XAMCORE_4_0
+using CFNetwork;
+using CoreFoundation;
+using CF=CoreFoundation;
+#elif XAMCORE_2_0
+using CoreServices;
+using CoreFoundation;
+using CF=CoreFoundation;
+#else
+using MonoTouch.CoreServices;
+using MonoTouch.CoreFoundation;
+using CF=MonoTouch.CoreFoundation;
+#endif
+
+namespace System.Net.Http
+{
+       public class CFNetworkHandler : HttpMessageHandler
+       {
+               class StreamBucket
+               {
+                       public TaskCompletionSource<HttpResponseMessage> Response;
+                       public HttpRequestMessage Request;
+                       public CancellationTokenRegistration CancellationTokenRegistration;
+                       public CFContentStream ContentStream;
+
+                       public void Close ()
+                       {
+                               CancellationTokenRegistration.Dispose ();
+                               ContentStream.Close ();
+                       }
+               }
+
+               bool allowAutoRedirect;
+               bool sentRequest;
+               bool useSystemProxy;
+               CookieContainer cookies;
+
+               Dictionary<IntPtr, StreamBucket> streamBuckets;
+
+               public CFNetworkHandler ()
+               {
+                       allowAutoRedirect = true;
+                       streamBuckets = new Dictionary<IntPtr, StreamBucket> ();
+               }
+
+               void EnsureModifiability ()
+               {
+                       if (sentRequest)
+                               throw new InvalidOperationException (
+                                       "This instance has already started one or more requests. " +
+                                       "Properties can only be modified before sending the first request.");
+               }
+
+               public bool AllowAutoRedirect {
+                       get {
+                               return allowAutoRedirect;
+                       }
+                       set {
+                               EnsureModifiability ();
+                               allowAutoRedirect = value;
+                       }
+               }
+
+               public CookieContainer CookieContainer {
+                       get {
+                               return cookies;
+                       }
+                       set {
+                               EnsureModifiability ();
+                               cookies = value;
+                       }
+               }
+
+               public bool UseSystemProxy {
+                       get {
+                               return useSystemProxy;
+                       }
+                       set {
+                               EnsureModifiability ();
+                               useSystemProxy = value;
+                       }
+               }
+
+               // TODO: Add more properties
+
+               protected override void Dispose (bool disposing)
+               {
+                       // TODO: CloseStream remaining stream buckets if there are any
+
+                       base.Dispose (disposing);
+               }
+
+               CFHTTPMessage CreateWebRequestAsync (HttpRequestMessage request)
+               {
+                       var req = CFHTTPMessage.CreateRequest (request.RequestUri, request.Method.Method, request.Version);
+
+                       // TODO:
+/*
+                       if (wr.ProtocolVersion == HttpVersion.Version10) {
+                               wr.KeepAlive = request.Headers.ConnectionKeepAlive;
+                       } else {
+                               wr.KeepAlive = request.Headers.ConnectionClose != true;
+                       }
+
+                       if (useDefaultCredentials) {
+                               wr.UseDefaultCredentials = true;
+                       } else {
+                               wr.Credentials = credentials;
+                       }
+
+                       if (useProxy) {
+                               wr.Proxy = proxy;
+                       }
+*/
+                       if (cookies != null) {
+                               string cookieHeader = cookies.GetCookieHeader (request.RequestUri);
+                               if (cookieHeader != "")
+                                       req.SetHeaderFieldValue ("Cookie", cookieHeader);
+                       }
+
+                       foreach (var header in request.Headers) {
+                               foreach (var value in header.Value) {
+                                       req.SetHeaderFieldValue (header.Key, value);
+                               }
+                       }
+
+                       if (request.Content != null) {
+                               foreach (var header in request.Content.Headers) {
+                                       foreach (var value in header.Value) {
+                                               req.SetHeaderFieldValue (header.Key, value);
+                                       }
+                               }
+                       }
+
+                       return req;
+               }
+
+               protected internal override async Task<HttpResponseMessage> SendAsync (HttpRequestMessage request, CancellationToken cancellationToken)
+               {
+                       sentRequest = true;
+
+                       CFHTTPStream stream;
+                       using (var message = CreateWebRequestAsync (request))
+                       {
+                               if (request.Content != null) {
+                                       var data = await request.Content.ReadAsByteArrayAsync ().ConfigureAwait (false);
+                                       message.SetBody (data);
+                               }
+
+                               stream = CFHTTPStream.CreateForHTTPRequest (message);
+                       }
+
+                       if (useSystemProxy) {
+                               var proxies = CF.CFNetwork.GetSystemProxySettings ();
+                               if (proxies.HTTPEnable) {
+                                       stream.SetProxy (proxies);
+                               }
+                       }
+
+                       stream.ShouldAutoredirect = allowAutoRedirect;
+                       stream.HasBytesAvailableEvent += HandleHasBytesAvailableEvent;
+                       stream.ErrorEvent += HandleErrorEvent;
+                       stream.ClosedEvent += HandleClosedEvent;
+
+                       var response = new TaskCompletionSource<HttpResponseMessage> ();
+
+                       if (cancellationToken.IsCancellationRequested) {
+                               response.SetCanceled ();
+                               return await response.Task;
+                       }
+
+                       var bucket = new StreamBucket () {
+                               Request = request,
+                               Response = response,
+                       };
+
+                       streamBuckets.Add (stream.Handle, bucket);
+
+                       //
+                       // Always schedule stream events handling on main-loop. Due to ConfigureAwait (false) we may end up
+                       // on any thread-pool thread which may not have run-loop running
+                       //
+#if XAMCORE_2_0
+                       stream.EnableEvents (CF.CFRunLoop.Main, CF.CFRunLoop.ModeCommon);
+#else
+                       stream.EnableEvents (CF.CFRunLoop.Main, CF.CFRunLoop.CFRunLoopCommonModes);
+#endif
+
+                       stream.Open ();
+
+                       bucket.CancellationTokenRegistration = cancellationToken.Register (() => {
+                               StreamBucket bucket2;
+                               if (!streamBuckets.TryGetValue (stream.Handle, out bucket2))
+                                       return;
+
+                               bucket2.Response.TrySetCanceled ();
+                               CloseStream (stream);
+                       });
+
+                       return await response.Task;
+               }
+
+               void HandleErrorEvent (object sender, CFStream.StreamEventArgs e)
+               {
+                       var stream = (CFHTTPStream)sender;
+
+                       StreamBucket bucket;
+                       if (!streamBuckets.TryGetValue (stream.Handle, out bucket))
+                               return;
+
+                       bucket.Response.TrySetException (stream.GetError ());
+                       CloseStream (stream);
+               }
+
+               void HandleClosedEvent (object sender, CFStream.StreamEventArgs e)
+               {
+                       var stream = (CFHTTPStream)sender;
+                       CloseStream (stream);
+               }
+
+               void CloseStream (CFHTTPStream stream)
+               {
+                       StreamBucket bucket;
+                       if (streamBuckets.TryGetValue (stream.Handle, out bucket)) {
+                               bucket.Close ();
+                               streamBuckets.Remove (stream.Handle);
+                       }
+
+                       stream.Close ();
+               }
+
+               void HandleHasBytesAvailableEvent (object sender, CFStream.StreamEventArgs e)
+               {
+                       var stream = (CFHTTPStream) sender;
+
+                       StreamBucket bucket;
+                       if (!streamBuckets.TryGetValue (stream.Handle, out bucket))
+                               return;
+
+                       if (bucket.Response.Task.IsCompleted) {
+                               bucket.ContentStream.ReadStreamData ();
+                               return;
+                       }
+
+                       var header = stream.GetResponseHeader ();
+
+                       // Is this possible?
+                       if (!header.IsHeaderComplete)
+                               throw new NotImplementedException ();
+
+                       bucket.ContentStream = new CFContentStream (stream);
+                               
+                       var response_msg = new HttpResponseMessage (header.ResponseStatusCode);
+                       response_msg.RequestMessage = bucket.Request;
+                       response_msg.ReasonPhrase = header.ResponseStatusLine;
+                       response_msg.Content = bucket.ContentStream;
+
+                       var fields = header.GetAllHeaderFields ();
+                       if (fields != null) {
+                               foreach (var entry in fields) {
+                                       if (entry.Key == null)
+                                               continue;
+
+                                       var key = entry.Key.ToString ();
+                                       var value = entry.Value == null ? string.Empty : entry.Value.ToString ();
+                                       HttpHeaders item_headers;
+                                       if (HttpHeaders.GetKnownHeaderKind (key) == Headers.HttpHeaderKind.Content) {
+                                               item_headers = response_msg.Content.Headers;
+                                       } else {
+                                               item_headers = response_msg.Headers;
+
+                                               if (cookies != null && (key == "Set-Cookie" || key == "Set-Cookie2"))
+                                                       AddCookie (value, bucket.Request.RequestUri, key);
+                                       }
+
+                                       item_headers.TryAddWithoutValidation (key, value);
+                               }
+                       }
+
+                       bucket.Response.TrySetResult (response_msg);
+
+                       bucket.ContentStream.ReadStreamData ();
+               }
+
+               void AddCookie (string value, Uri uri, string header)
+               {
+                       CookieCollection cookies1 = null;
+                       try {
+                               cookies1 = cookies.CookieCutter (uri, header, value, false);
+                       } catch {
+                       }
+
+                       if (cookies1 != null && cookies1.Count != 0) 
+                               cookies.Add (cookies1);
+               }
+       }
+}
index eb70cc576c78dd095f011ab76dde239e0dc78642..08925bbaf2dec3812ae4d53b2780d9a9aec621ec 100644 (file)
@@ -56,6 +56,7 @@
   <Types>
     <Namespace Name="System.Net.Http">
       <Type Name="ByteArrayContent" Kind="Class" />
+      <Type Name="CFNetworkHandler" Kind="Class" />
       <Type Name="ClientCertificateOption" Kind="Enumeration" />
       <Type Name="DelegatingHandler" Kind="Class" />
       <Type Name="FormUrlEncodedContent" Kind="Class" />
diff --git a/mcs/class/System.Net.Http/HttpClientEx.cs b/mcs/class/System.Net.Http/HttpClientEx.cs
new file mode 100644 (file)
index 0000000..59456d6
--- /dev/null
@@ -0,0 +1,224 @@
+using System;
+using System.IO;
+using System.Net;
+#if XAMCORE_2_0
+using CoreFoundation;
+using Foundation;
+using ObjCRuntime;
+#elif MONOMAC
+using MonoMac.CoreFoundation;
+using MonoMac.Foundation;
+using MonoMac.ObjCRuntime;
+#else
+using MonoTouch.CoreFoundation;
+using MonoTouch.Foundation;
+using MonoTouch.ObjCRuntime;
+#endif
+
+#if SYSTEM_NET_HTTP && !MONOMAC
+namespace System.Net.Http {
+
+       public partial class HttpClient {
+
+               public HttpClient ()
+                       : this (GetDefaultHandler (), true)
+               {
+               }
+
+               // note: the linker will re-write this to only reference the selected handler
+               // but we want this to work "as expected" even if the application is not being linked
+               static HttpMessageHandler GetDefaultHandler ()
+               {
+                       return RuntimeOptions.GetHttpMessageHandler ();
+               }
+       }
+#else
+// due to historical reasons (around CFNetwork) Xamarin.Mac includes this inside it's profile assembly
+// and not a custom System.Net.Http assembly
+namespace Foundation {
+#endif
+
+       partial class NSUrlSessionHandler {
+
+               bool allowAutoRedirect;
+               ICredentials credentials;
+               bool sentRequest;
+
+               public bool AllowAutoRedirect {
+                       get {
+                               return allowAutoRedirect;
+                       }
+                       set {
+                               EnsureModifiability ();
+                               allowAutoRedirect = value;
+                       }
+               }
+
+               public ICredentials Credentials {
+                       get {
+                               return credentials;
+                       }
+                       set {
+                               EnsureModifiability ();
+                               credentials = value;
+                       }
+               }
+
+               internal void EnsureModifiability ()
+               {
+                       if (sentRequest)
+                               throw new InvalidOperationException (
+                                       "This instance has already started one or more requests. " +
+                                       "Properties can only be modified before sending the first request.");
+               }
+
+               // almost identical to ModernHttpClient version but it uses the constants from monotouch.dll | Xamarin.[iOS|WatchOS|TVOS].dll
+               static Exception createExceptionForNSError(NSError error)
+               {
+                       var webExceptionStatus = WebExceptionStatus.UnknownError;
+
+                       var innerException = new NSErrorException(error);
+
+                       // errors that exists in both share the same error code, so we can use a single switch/case
+                       // this also ease watchOS integration as if does not expose CFNetwork but (I would not be 
+                       // surprised if it)could return some of it's error codes
+#if MONOTOUCH_WATCH
+                       if (error.Domain == NSError.NSUrlErrorDomain) {
+#else
+                       if ((error.Domain == NSError.NSUrlErrorDomain) || (error.Domain == NSError.CFNetworkErrorDomain)) {
+#endif
+                               // Parse the enum into a web exception status or exception. Some
+                               // of these values don't necessarily translate completely to
+                               // what WebExceptionStatus supports, so made some best guesses
+                               // here.  For your reading pleasure, compare these:
+                               //
+                               // Apple docs: https://developer.apple.com/library/mac/documentation/Cocoa/Reference/Foundation/Miscellaneous/Foundation_Constants/index.html#//apple_ref/doc/constant_group/URL_Loading_System_Error_Codes
+                               // .NET docs: http://msdn.microsoft.com/en-us/library/system.net.webexceptionstatus(v=vs.110).aspx
+                               switch ((NSUrlError) (long) error.Code) {
+                               case NSUrlError.Cancelled:
+                               case NSUrlError.UserCancelledAuthentication:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) NSNetServicesStatus.CancelledError:
+#endif
+                                       // No more processing is required so just return.
+                                       return new OperationCanceledException(error.LocalizedDescription, innerException);
+                               case NSUrlError.BadURL:
+                               case NSUrlError.UnsupportedURL:
+                               case NSUrlError.CannotConnectToHost:
+                               case NSUrlError.ResourceUnavailable:
+                               case NSUrlError.NotConnectedToInternet:
+                               case NSUrlError.UserAuthenticationRequired:
+                               case NSUrlError.InternationalRoamingOff:
+                               case NSUrlError.CallIsActive:
+                               case NSUrlError.DataNotAllowed:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.Socks5BadCredentials:
+                               case (NSUrlError) CFNetworkErrors.Socks5UnsupportedNegotiationMethod:
+                               case (NSUrlError) CFNetworkErrors.Socks5NoAcceptableMethod:
+                               case (NSUrlError) CFNetworkErrors.HttpAuthenticationTypeUnsupported:
+                               case (NSUrlError) CFNetworkErrors.HttpBadCredentials:
+                               case (NSUrlError) CFNetworkErrors.HttpBadURL:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.ConnectFailure;
+                                       break;
+                               case NSUrlError.TimedOut:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.NetServiceTimeout:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.Timeout;
+                                       break;
+                               case NSUrlError.CannotFindHost:
+                               case NSUrlError.DNSLookupFailed:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.HostNotFound:
+                               case (NSUrlError) CFNetworkErrors.NetServiceDnsServiceFailure:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.NameResolutionFailure;
+                                       break;
+                               case NSUrlError.DataLengthExceedsMaximum:
+                                       webExceptionStatus = WebExceptionStatus.MessageLengthLimitExceeded;
+                                       break;
+                               case NSUrlError.NetworkConnectionLost:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.HttpConnectionLost:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.ConnectionClosed;
+                                       break;
+                               case NSUrlError.HTTPTooManyRedirects:
+                               case NSUrlError.RedirectToNonExistentLocation:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.HttpRedirectionLoopDetected:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.ProtocolError;
+                                       break;
+                               case NSUrlError.RequestBodyStreamExhausted:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.SocksUnknownClientVersion:
+                               case (NSUrlError) CFNetworkErrors.SocksUnsupportedServerVersion:
+                               case (NSUrlError) CFNetworkErrors.HttpParseFailure:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.SendFailure;
+                                       break;
+                               case NSUrlError.BadServerResponse:
+                               case NSUrlError.ZeroByteResource:
+                               case NSUrlError.CannotDecodeRawData:
+                               case NSUrlError.CannotDecodeContentData:
+                               case NSUrlError.CannotParseResponse:
+                               case NSUrlError.FileDoesNotExist:
+                               case NSUrlError.FileIsDirectory:
+                               case NSUrlError.NoPermissionsToReadFile:
+                               case NSUrlError.CannotLoadFromNetwork:
+                               case NSUrlError.CannotCreateFile:
+                               case NSUrlError.CannotOpenFile:
+                               case NSUrlError.CannotCloseFile:
+                               case NSUrlError.CannotWriteToFile:
+                               case NSUrlError.CannotRemoveFile:
+                               case NSUrlError.CannotMoveFile:
+                               case NSUrlError.DownloadDecodingFailedMidStream:
+                               case NSUrlError.DownloadDecodingFailedToComplete:
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.Socks4RequestFailed:
+                               case (NSUrlError) CFNetworkErrors.Socks4IdentdFailed:
+                               case (NSUrlError) CFNetworkErrors.Socks4IdConflict:
+                               case (NSUrlError) CFNetworkErrors.Socks4UnknownStatusCode:
+                               case (NSUrlError) CFNetworkErrors.Socks5BadState:
+                               case (NSUrlError) CFNetworkErrors.Socks5BadResponseAddr:
+                               case (NSUrlError) CFNetworkErrors.CannotParseCookieFile:
+                               case (NSUrlError) CFNetworkErrors.NetServiceUnknown:
+                               case (NSUrlError) CFNetworkErrors.NetServiceCollision:
+                               case (NSUrlError) CFNetworkErrors.NetServiceNotFound:
+                               case (NSUrlError) CFNetworkErrors.NetServiceInProgress:
+                               case (NSUrlError) CFNetworkErrors.NetServiceBadArgument:
+                               case (NSUrlError) CFNetworkErrors.NetServiceInvalid:
+#endif
+                                       webExceptionStatus = WebExceptionStatus.ReceiveFailure;
+                                       break;
+                               case NSUrlError.SecureConnectionFailed:
+                                       webExceptionStatus = WebExceptionStatus.SecureChannelFailure;
+                                       break;
+                               case NSUrlError.ServerCertificateHasBadDate:
+                               case NSUrlError.ServerCertificateHasUnknownRoot:
+                               case NSUrlError.ServerCertificateNotYetValid:
+                               case NSUrlError.ServerCertificateUntrusted:
+                               case NSUrlError.ClientCertificateRejected:
+                               case NSUrlError.ClientCertificateRequired:
+                                       webExceptionStatus = WebExceptionStatus.TrustFailure;
+                                       break;
+#if !MONOTOUCH_WATCH
+                               case (NSUrlError) CFNetworkErrors.HttpProxyConnectionFailure:
+                               case (NSUrlError) CFNetworkErrors.HttpBadProxyCredentials:
+                               case (NSUrlError) CFNetworkErrors.PacFileError:
+                               case (NSUrlError) CFNetworkErrors.PacFileAuth:
+                               case (NSUrlError) CFNetworkErrors.HttpsProxyConnectionFailure:
+                               case (NSUrlError) CFNetworkErrors.HttpsProxyFailureUnexpectedResponseToConnectMethod:
+                                       webExceptionStatus = WebExceptionStatus.RequestProhibitedByProxy;
+                                       break;
+#endif
+                               }
+                       } 
+
+                       // Always create a WebException so that it can be handled by the client.
+                       return new WebException(error.LocalizedDescription, innerException); //, webExceptionStatus, response: null);
+               }
+       }
+}
index aa3cdf921e56f3563c5d53c213ed72cf7c2cd1a9..9abcf2e80f62071ca0cf14a470dfaed396b3596a 100644 (file)
@@ -6,7 +6,11 @@ LIBRARY = System.Net.Http.dll
 
 LIB_REFS = System.Core System
 LIB_MCS_FLAGS = $(EXTRA_LIB_MCS_FLAGS)
+ifeq (monodroid,$(PROFILE))
+LIB_MCS_FLAGS += -d:XAMARIN_MODERN
+endif
 
-TEST_MCS_FLAGS = -r:System.dll -r:System.Core.dll
+TEST_LIB_REFS = System System.Core
+TEST_MCS_FLAGS =
 
 include ../../build/library.make
diff --git a/mcs/class/System.Net.Http/System.Net.Http/HttpClient.android.cs b/mcs/class/System.Net.Http/System.Net.Http/HttpClient.android.cs
new file mode 100644 (file)
index 0000000..f48b49c
--- /dev/null
@@ -0,0 +1,38 @@
+using System;
+using System.Reflection;
+
+namespace System.Net.Http {
+       public partial class HttpClient {
+
+               public HttpClient ()
+                       : this (GetDefaultHandler (), true)
+               {
+               }
+
+               static HttpMessageHandler GetDefaultHandler ()
+               {
+                       Type type = Type.GetType("Android.Runtime.AndroidEnvironment, Mono.Android");
+                       if (type == null)
+                               return GetFallback ("Invalid Mono.Android assembly? Cannot find Android.Runtime.AndroidEnvironment");
+
+                       MethodInfo method = type.GetMethod ("GetHttpMessageHandler", BindingFlags.Static | BindingFlags.NonPublic);
+                       if (method == null)
+                               return GetFallback ("Your Xamarin.Android version does not support obtaining of the custom HttpClientHandler");
+
+                       object ret = method.Invoke (null, null);
+                       if (ret == null)
+                               return GetFallback ("Xamarin.Android returned no custom HttpClientHandler");
+
+                       var handler = ret as HttpMessageHandler;
+                       if (handler == null)
+                               return GetFallback ($"{ret?.GetType()} is not a valid HttpMessageHandler");
+                       return handler;
+               }
+
+               static HttpMessageHandler GetFallback (string message)
+               {
+                       Console.WriteLine (message + ". Defaulting to System.Net.Http.HttpClientHandler");
+                       return new HttpClientHandler ();
+               }
+       }
+}
diff --git a/mcs/class/System.Net.Http/System.Net.Http/HttpClient.mac.cs b/mcs/class/System.Net.Http/System.Net.Http/HttpClient.mac.cs
new file mode 100644 (file)
index 0000000..42f664c
--- /dev/null
@@ -0,0 +1,23 @@
+using System;
+using System.Reflection;
+
+[assembly:System.Runtime.CompilerServices.InternalsVisibleTo ("Xamarin.Mac, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
+
+namespace System.Net.Http {
+       public partial class HttpClient {
+
+               public HttpClient ()
+                       : this (GetDefaultHandler (), true)
+               {
+               }
+
+               // note: the linker will re-write ObjCRuntime.RuntimeOptions.GetHttpMessageHandler to return the correct type
+               // unlike, XI where this method itself gets rewritten during linking
+               static HttpMessageHandler GetDefaultHandler ()
+               {
+                       Type type = Type.GetType("ObjCRuntime.RuntimeOptions, Xamarin.Mac");
+                       var method = type.GetMethod ("GetHttpMessageHandler", BindingFlags.Static | BindingFlags.NonPublic);
+                       return (HttpMessageHandler)method.Invoke (null, null);
+               }
+       }
+}
index 52a64788971e226d362bf1cf43a8a090ed8a9204..4d9265a6ac76f8e3640e82e2e75e1fa6189b8ee6 100644 (file)
@@ -152,15 +152,16 @@ namespace MonoTests.System.Net.Http
 
                const int WaitTimeout = 5000;
 
-               string port, TestHost, LocalServer;
+               string TestHost, LocalServer;
+               int port;
 
                [SetUp]
                public void SetupFixture ()
                {
                        if (Environment.OSVersion.Platform == PlatformID.Win32NT) {
-                               port = "810";
+                               port = 810;
                        } else {
-                               port = "8810";
+                               port = 8810;
                        }
 
                        TestHost = "localhost:" + port;
@@ -1080,9 +1081,20 @@ namespace MonoTests.System.Net.Http
                                var response = l.Response;
 
                                response.StatusCode = (int)HttpStatusCode.Moved;
-                               response.RedirectLocation = "http://xamarin.com/";
+                               response.RedirectLocation = "http://localhost:8811/";
                        });
 
+                       var listener2 = CreateListener (l => {
+                               var response = l.Response;
+
+                               response.StatusCode = (int)HttpStatusCode.OK;
+                               response.OutputStream.WriteByte (0x68);
+                               response.OutputStream.WriteByte (0x65);
+                               response.OutputStream.WriteByte (0x6c);
+                               response.OutputStream.WriteByte (0x6c);
+                               response.OutputStream.WriteByte (0x6f);
+                       }, 8811);
+
                        try {
                                var chandler = new HttpClientHandler ();
                                chandler.AllowAutoRedirect = true;
@@ -1091,10 +1103,13 @@ namespace MonoTests.System.Net.Http
                                var r = client.GetAsync (LocalServer);
                                Assert.IsTrue (r.Wait (WaitTimeout), "#1");
                                var resp = r.Result;
-                               Assert.AreEqual ("http://xamarin.com/", resp.RequestMessage.RequestUri.AbsoluteUri, "#2");
+                               Assert.AreEqual ("http://localhost:8811/", resp.RequestMessage.RequestUri.AbsoluteUri, "#2");
+                               Assert.AreEqual ("hello", resp.Content.ReadAsStringAsync ().Result, "#3");
                        } finally {
                                listener.Abort ();
                                listener.Close ();
+                               listener2.Abort ();
+                               listener2.Close ();
                        }
                }
 
@@ -1151,6 +1166,11 @@ namespace MonoTests.System.Net.Http
                }
 
                HttpListener CreateListener (Action<HttpListenerContext> contextAssert)
+               {
+                       return CreateListener (contextAssert, port);
+               }
+
+               HttpListener CreateListener (Action<HttpListenerContext> contextAssert, int port)
                {
                        var l = new HttpListener ();
                        l.Prefixes.Add (string.Format ("http://+:{0}/", port));
diff --git a/mcs/class/System.Net.Http/monodroid_System.Net.Http.dll.sources b/mcs/class/System.Net.Http/monodroid_System.Net.Http.dll.sources
new file mode 100644 (file)
index 0000000..acaa6a3
--- /dev/null
@@ -0,0 +1,2 @@
+#include System.Net.Http.dll.sources
+System.Net.Http/HttpClient.android.cs
index fbffe9e7634bb2e8d42c512f49453edf60a03b1e..216e48da9cdbcb384ba0ecc8b3c4aa814c2f4ce5 100644 (file)
@@ -1 +1,2 @@
 #include System.Net.Http.dll.sources
+System.Net.Http/HttpClient.mac.cs
index fbffe9e7634bb2e8d42c512f49453edf60a03b1e..216e48da9cdbcb384ba0ecc8b3c4aa814c2f4ce5 100644 (file)
@@ -1 +1,2 @@
 #include System.Net.Http.dll.sources
+System.Net.Http/HttpClient.mac.cs
index 8e5efe308ce8a52ef8d8ea3c6492ee93188715aa..fc666baf51ca53b437ad7b1eb98e476efcad6f5b 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Core.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Interfaces.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
index e05d3c0236e2cb69a33984069812a7674007bf90..f7f8f44e195f2eab4d452a18f622827a8a0742bd 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Linq.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Core.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
index ec5e06a73a84530412b32ec9723312c695c01319..0db9de14052ca03748e8ce734006ee299325b53f 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Observable.Aliases.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq System.Reactive.Providers
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Providers.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
index 1a8675dc69af0736a30654aa87cc48b7952b9cd4..0333c27f2e74bd531e34c5af1666da5275c76ed4 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.PlatformServices.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Linq.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
@@ -35,7 +34,8 @@ ifndef NO_TASK_DELAY
 LIB_MCS_FLAGS += -d:NO_TASK_DELAY
 endif
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -r:Mono.Reactive.Tests.dll
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
+TEST_LIB_REFS = Mono.Reactive.Tests
 
 EXTRA_DISTFILES = more_build_args $(RESX_RESOURCES:.resources=.resx) $(PREBUILT)
 
index 9aedac157d73c36b33b7a525f8b1c8d656141fc1..ab1f274d1503cf65d124a5069e797bedbc72cc65 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Providers.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Linq.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
index 389920631a72cccac89543143e9e7a3f69839fce..1834e7aaa259e9de7bb25255053d6ad27feb0825 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Runtime.Remoting.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Reactive.Linq.dll
+               @more_build_args
 
 ifeq (2.1, $(FRAMEWORK_VERSION))
 LIB_MCS_FLAGS += -d:NO_TASK_DELAY
index e2f9d24fa92a02a9472f1aee4ecef2a3d479b0fa..ef3327d3e3e3dd39af41698bb97d9b7ef7d9d372 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Windows.Forms.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq System.Windows.Forms
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:System.Windows.Forms.dll
+               @more_build_args
 
 ifeq (2.1, $(FRAMEWORK_VERSION))
 LIB_MCS_FLAGS += -d:NO_TASK_DELAY -d:HAS_AWAIT
index 3c0654cfac387f4690791f0dd8a3b55a7de1e269..66a3ff14f6c6518b55254691c13c1d65fd52e02e 100644 (file)
@@ -5,8 +5,7 @@ include ../../build/rules.make
 LIBRARY = System.Reactive.Windows.Threading.dll
 LIB_REFS = System System.Core System.Reactive.Interfaces System.Reactive.Core System.Reactive.Linq WindowsBase
 LIB_MCS_FLAGS = \
-               @more_build_args \
-               -r:WindowsBase.dll
+               @more_build_args
 
 ifeq (true, $(GENERATE_RESOURCES))
 LIB_MCS_FLAGS += /define:GENERATING_RESOURCES
index 344d5669236655ba19abb49663689453c3d71af9..323d4241eb5ce80ee8106733b36fce329cd1cdc6 100644 (file)
@@ -4,10 +4,15 @@ include ../../build/rules.make
 
 LIBRARY = System.Runtime.Remoting.dll
 
-LIB_REFS = System System.Web System.Xml System.Runtime.Serialization.Formatters.Soap
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_REFS = System System.Xml System.Runtime.Serialization.Formatters.Soap
+LIB_MCS_FLAGS =
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:618 /r:System.Runtime.Remoting.dll
+ifndef NO_SYSTEM_WEB_DEPENDENCY
+LIB_REFS += System.Web
+endif
+
+TEST_MCS_FLAGS = -nowarn:618
+TEST_LIB_REFS = System System.Xml
 
 TEST_MONO_PATH = .
 
diff --git a/mcs/class/System.Runtime.Remoting/xammac_net_4_5_System.Runtime.Remoting.dll.sources b/mcs/class/System.Runtime.Remoting/xammac_net_4_5_System.Runtime.Remoting.dll.sources
new file mode 100644 (file)
index 0000000..cadd275
--- /dev/null
@@ -0,0 +1,56 @@
+Assembly/AssemblyInfo.cs
+../../build/common/Consts.cs
+../../build/common/Locale.cs
+../../build/common/MonoTODOAttribute.cs
+System.Runtime.Remoting.Channels/BinaryClientFormatterSink.cs
+System.Runtime.Remoting.Channels/BinaryClientFormatterSinkProvider.cs
+System.Runtime.Remoting.Channels/BinaryCore.cs
+System.Runtime.Remoting.Channels/BinaryServerFormatterSink.cs
+System.Runtime.Remoting.Channels/BinaryServerFormatterSinkProvider.cs
+System.Runtime.Remoting.Channels/ChannelCore.cs
+System.Runtime.Remoting.Channels/CommonTransportKeys.cs
+System.Runtime.Remoting.Channels/IAuthorizeRemotingConnection.cs
+System.Runtime.Remoting.Channels/RemotingThreadPool.cs
+System.Runtime.Remoting.Channels/SoapClientFormatterSink.cs
+System.Runtime.Remoting.Channels/SoapCore.cs
+System.Runtime.Remoting.Channels/SoapServerFormatterSink.cs
+System.Runtime.Remoting.Channels/SoapClientFormatterSinkProvider.cs
+System.Runtime.Remoting.Channels/SoapServerFormatterSinkProvider.cs
+System.Runtime.Remoting.Channels/SoapMessageFormatter.cs
+System.Runtime.Remoting.Channels/SocketCachePolicy.cs
+System.Runtime.Remoting.Channels.Ipc/IpcChannel.cs
+System.Runtime.Remoting.Channels.Ipc/IpcClientChannel.cs
+System.Runtime.Remoting.Channels.Ipc/IpcServerChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/IpcTransport.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/IpcChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/IpcChannelHelper.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/IpcClientChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/IpcServerChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeClient.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeException.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeHelper.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeListener.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeSocket.cs
+System.Runtime.Remoting.Channels.Ipc.Win32/NamedPipeStream.cs
+System.Runtime.Remoting.Channels.Ipc.Unix/IpcChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Unix/IpcClientChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Unix/IpcServerChannel.cs
+System.Runtime.Remoting.Channels.Ipc.Unix/UnixChannelLoader.cs
+System.Runtime.Remoting.Channels.Tcp/TcpChannel.cs
+System.Runtime.Remoting.Channels.Tcp/TcpClientChannel.cs
+System.Runtime.Remoting.Channels.Tcp/TcpMessageIO.cs
+System.Runtime.Remoting.Channels.Tcp/TcpServerChannel.cs
+System.Runtime.Remoting.Channels.Tcp/TcpServerTransportSink.cs
+System.Runtime.Remoting.Channels.Tcp/TcpClientTransportSinkProvider.cs
+System.Runtime.Remoting.Channels.Tcp/TcpClientTransportSink.cs
+System.Runtime.Remoting.Channels.Tcp/TcpConnectionPool.cs
+System.Runtime.Remoting.MetadataServices/MetaData.cs
+System.Runtime.Remoting.MetadataServices/MetaDataExporter.cs
+System.Runtime.Remoting.MetadataServices/MetaDataCodeGenerator.cs
+System.Runtime.Remoting.MetadataServices/SdlChannelSinkProvider.cs
+System.Runtime.Remoting.MetadataServices/ServiceType.cs
+System.Runtime.Remoting.MetadataServices/SUDSParserException.cs
+System.Runtime.Remoting.MetadataServices/SdlChannelSink.cs
+System.Runtime.Remoting.MetadataServices/SdlType.cs
+System.Runtime.Remoting.MetadataServices/SUDSGeneratorException.cs
+System.Runtime.Remoting.Services/RemotingClientProxy.cs
index 76d3270616d3b94427d798d02bc23435b0124bfe..7a673f01fa3b3245627fb9114f3f97446c6ca515 100644 (file)
@@ -6,8 +6,10 @@ include ../../build/rules.make
 
 LIBRARY = System.Runtime.Serialization.Formatters.Soap.dll
 LIB_REFS = System.Xml
-LIB_MCS_FLAGS = /r:$(corlib)
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -r:System.dll -nowarn:0618 -nowarn:219 -nowarn:169
+LIB_MCS_FLAGS =
+
+TEST_LIB_REFS = System
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 
 EXTRA_DISTFILES = \
        README          \
index dbacda112e889f0a83533f3e0dd6fdf890da770f..487ff5f1dd7ecafac8d3e3f3972db9435188bd3c 100644 (file)
@@ -23,7 +23,7 @@ using System.Runtime.CompilerServices;
 // You can specify all values by your own or you can build default build and revision\r
 // numbers with the '*' character (the default):\r
 \r
-[assembly: AssemblyVersion("1.0.*")]\r
+[assembly: AssemblyVersion("1.0.0.0")]\r
 \r
 // The following attributes specify the key for the sign of your assembly. See the\r
 // .NET Framework documentation for more information about signing.\r
index 21d8e716a39187f157f2511d834a5d5f4bf9add5..03b78193d75396a3290ce28ea264171a22647a4c 100644 (file)
@@ -11,6 +11,7 @@ LIB_MCS_FLAGS = \
                -d:NO_DYNAMIC_CODEGEN \
                /nowarn:168,169,219,414 \
                $(RESOURCE_FILES:%=/resource:%)
+TXT_RESOURCE_STRINGS = ../../../external/referencesource/System.Runtime.Serialization/System.Runtime.Serialization.txt
 
 ifneq (2.1, $(FRAMEWORK_VERSION))
 LIB_REFS += System.Data System.Configuration
@@ -27,8 +28,8 @@ TEST_RESOURCE_FILES = \
        Test/Resources/WSDL/collections.wsdl    \
        Test/Resources/WSDL/custom-collections.wsdl
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) /r:System.ServiceModel.dll /r:System.Web.Services.dll \
-       $(TEST_RESOURCE_FILES:%=/resource:%)
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(TEST_RESOURCE_FILES:%=/resource:%)
+TEST_LIB_REFS = System.ServiceModel System.Web.Services
 
 EXTRA_DISTFILES = $(RESOURCE_FILES) $(TEST_RESOURCE_FILES) \
        Test/Resources/FrameworkTypes/* \
index ae10d9fefa1675bfa8acd5a1ea6a57ad5edb09c7..856841518bf78dd21a75df312b81a2dad878ff36 100644 (file)
-using System.Globalization;
-
-#region "copy of ../../build/common/SR.cs"
-
-namespace System.Runtime.Serialization
+//
+// This file was generated by txt2sr tool
+//
+namespace System.Runtime.Serialization {
+partial class SR
 {
-       static partial class SR 
-       {
-
-        internal static string GetString(string name, params object[] args)
-        {
-                return GetString (CultureInfo.InvariantCulture, name, args);
-        }
-
-        internal static string GetString(CultureInfo culture, string name, params object[] args) {
-                return string.Format (culture, name, args);
-        }
-
-        internal static string GetString(string name)
-        {
-                return name;
-        }
-
-        internal static string GetString(CultureInfo culture, string name)
-        {
-                return name;
-        }
+       public const string ArrayExceededSize = "Array length '{0}' provided by the get-only collection of type '{1}' is less than the number of array elements found in the input stream.  Consider increasing the length of the array.";
+       public const string ArrayExceededSizeAttribute = "Array length '{0}' provided by Size attribute is not equal to the number of array elements '{1}' from namespace '{2}' found.";
+       public const string ArrayTypeIsNotSupported = "An internal error has occurred. '{0}[]' is not supported when generating code for serialization.";
+       public const string CannotDeserializeRefAtTopLevel = "Cannot deserialize since root element references unrecognized object with id '{0}'.";
+       public const string CannotLoadMemberType = "Cannot load member type '{0}'.";
+       public const string CannotSerializeObjectWithCycles = "Object graph for type '{0}' contains cycles and cannot be serialized if references are not tracked. Consider using the DataContractAttribute with the IsReference property set to true.";
+       public const string CanOnlyStoreIntoArgOrLocGot0 = "An internal error has occurred. Data can only be stored into ArgBuilder or LocalBuilder. Got: {0}.";
+       public const string CharIsInvalidPrimitive = "An internal error has occurred. Char is not a valid schema primitive and should be treated as int in DataContract.";
+       public const string CallbackMustReturnVoid = "Serialization Callback '{1}' in type '{0}' must return void.";
+       public const string CallbackParameterInvalid = "Serialization Callback '{1}' in type '{0}' must have a single parameter of type '{2}'.";
+       public const string CallbacksCannotBeVirtualMethods = "Virtual Method '{0}' of type '{1}' cannot be marked with '{2}' attribute.";
+       public const string CollectionMustHaveAddMethod = "Collection type '{0}' does not have a valid Add method.";
+       public const string CollectionMustHaveGetEnumeratorMethod = "Collection type '{0}' does not have a valid GetEnumerator method.";
+       public const string CollectionMustHaveItemType = "Collection type '{0}' must have a non-null item type.";
+       public const string CollectionTypeCannotBeBuiltIn = "{0} is a built-in type and cannot be a collection.";
+       public const string CollectionTypeCannotHaveDataContract = "{0} has DataContractAttribute attribute.";
+       public const string CollectionTypeDoesNotHaveAddMethod = "{0} does not have a valid Add method with parameter of type '{1}'.";
+       public const string CollectionTypeDoesNotHaveDefaultCtor = "{0} does not have a default constructor.";
+       public const string CollectionTypeHasMultipleDefinitionsOfInterface = "{0} has multiple definitions of interface '{1}'.";
+       public const string CollectionTypeIsNotIEnumerable = "{0} does not implement IEnumerable interface.";
+       public const string DataContractCacheOverflow = "An internal error has occurred. DataContract cache overflow.";
+       public const string DataContractNamespaceAlreadySet = "ContractNamespaceAttribute attribute maps CLR namespace '{2}' to multiple data contract namespaces '{0}' and '{1}'. You can map a CLR namespace to only one data contract namespace.";
+       public const string DataContractNamespaceIsNotValid = "DataContract namespace '{0}' is not a valid URI.";
+       public const string DataContractNamespaceReserved = "DataContract namespace '{0}' cannot be specified since it is reserved.";
+       public const string DataMemberOnEnumField = "Member '{0}.{1}' has DataMemberAttribute attribute. Use EnumMemberAttribute attribute instead.";
+       public const string DcTypeNotFoundOnDeserialize = "Element '{2}:{3}' contains data of the '{0}:{1}' data contract. The deserializer has no knowledge of any type that maps to this contract. Add the type corresponding to '{1}' to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding it to the list of known types passed to DataContractSerializer.";
+       public const string DcTypeNotFoundOnSerialize = "Type '{0}' with data contract name '{1}:{2}' is not expected. Add any types not known statically to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding them to the list of known types passed to DataContractSerializer.";
+       public const string DcTypeNotResolvedOnDeserialize = "Element '{2}:{3}' contains data from a type that maps to the name '{0}:{1}'. The deserializer has no knowledge of any type that maps to this name. Consider changing the implementation of the ResolveName method on your DataContractResolver to return a non-null value for name '{1}' and namespace '{0}'.";
+       public const string DeserializedObjectWithIdNotFound = "Deserialized object with reference id '{0}' not found in stream.";
+       public const string DupContractInKnownTypes = "Type '{0}' cannot be added to list of known types since another type '{1}' with the same data contract name '{2}:{3}' is already present.";
+       public const string DupKeyValueName = "The collection data contract type '{0}' specifies the same value '{1}' for both the KeyName and the ValueName properties. This is not allowed. Consider changing either the KeyName or the ValueName property.";
+       public const string DupEnumMemberValue = "Type '{2}' contains two members '{0}' 'and '{1}' with the same name '{3}'. Multiple members with the same name in one type are not supported. Consider changing one of the member names using EnumMemberAttribute attribute.";
+       public const string DupMemberName = "Type '{2}' contains two members '{0}' 'and '{1}' with the same data member name '{3}'. Multiple members with the same name in one type are not supported. Consider changing one of the member names using DataMemberAttribute attribute.";
+       public const string DuplicateAttribute = "Invalid Callback. Method '{3}' in type '{2}' has both '{0}' and '{1}'.";
+       public const string DuplicateCallback = "Invalid attribute. Both '{0}' and '{1}' in type '{2}' have '{3}'.";
+       public const string EncounteredWithNameNamespace = "{0}. Encountered '{1}'  with name '{2}', namespace '{3}'.";
+       public const string EnumTypeCannotHaveIsReference = "Enum type '{0}' cannot have the IsReference setting of '{1}'. Either change the setting to '{2}', or remove it completely.";
+       public const string ErrorDeserializing = "There was an error deserializing the object {0}. {1}";
+       public const string ErrorInLine = "Error in line {0} position {1}.";
+       public const string ErrorIsStartObject = "There was an error checking start element of object {0}. {1}";
+       public const string ErrorSerializing = "There was an error serializing the object {0}. {1}";
+       public const string ErrorTypeInfo = "of type {0}";
+       public const string ErrorWriteEndObject = "There was an error writing end element of object {0}. {1}";
+       public const string ErrorWriteStartObject = "There was an error writing start element of object {0}. {1}";
+       public const string ExceededMaxItemsQuota = "Maximum number of items that can be serialized or deserialized in an object graph is '{0}'.";
+       public const string ExpectingElement = "Expecting element '{1}' from namespace '{0}'.";
+       public const string ExpectingElementAtDeserialize = "Expecting state '{0}' when ReadObject is called.";
+       public const string ExpectingEnd = "Expecting End'{0}'.";
+       public const string ExpectingState = "Expecting state '{0}'.";
+       public const string GenericNameBraceMismatch = "The data contract name '{0}' for type '{1}' has a curly brace '{{' that is not matched with a closing curly brace. Curly braces have special meaning in data contract names - they are used to customize the naming of data contracts for generic types.";
+       public const string GenericParameterNotValid = "In the data contract name for type '{1}', there are curly braces with '{0}' inside, which is an invalid value. Curly braces have special meaning in data contract names - they are used to customize the naming of data contracts for generic types. Based on the number of generic parameters this type has, the contents of the curly braces must either be a number between 0 and '{2}' to insert the name of the generic parameter at that index or the '#' symbol to insert a digest of the generic parameter namespaces.";
+       public const string InconsistentIsReference = "The IsReference setting for type '{0}' is '{1}', but the same setting for its parent class '{2}' is '{3}'. Derived types must have the same value for IsReference as the base type. Change the setting on type '{0}' to '{3}', or on type '{2}' to '{1}', or do not set IsReference explicitly.";
+       public const string IndexedPropertyCannotBeSerialized = "Property '{1}' in type '{0}' cannot be serialized because serialization of indexed properties is not supported.";
+       public const string InterfaceTypeCannotBeCreated = "Interface type '{0}' cannot be created. Consider replacing with a non-interface serializable type.";
+       public const string InvalidCollectionContractItemName = "Type '{0}' cannot have CollectionDataContractAttribute attribute ItemName set to null or empty string.";
+       public const string InvalidCollectionContractKeyName = "Type '{0}' cannot have CollectionDataContractAttribute attribute KeyName set to null or empty string.";
+       public const string InvalidCollectionContractKeyNoDictionary = "The collection data contract type '{0}' specifies '{1}' for the KeyName property. This is not allowed since the type is not IDictionary. Remove the setting for the KeyName property.";
+       public const string InvalidCollectionContractName = "Type '{0}' cannot have CollectionDataContractAttribute attribute Name set to null or empty string.";
+       public const string InvalidCollectionContractNamespace = "Type '{0}' cannot have CollectionDataContractAttribute attribute Namespace set to null.";
+       public const string InvalidCollectionContractValueName = "Type '{0}' cannot have CollectionDataContractAttribute attribute ValueName set to null or empty string.";
+       public const string InvalidCollectionContractValueNoDictionary = "The collection data contract type '{0}' specifies '{1}' for the ValueName property. This is not allowed since the type is not IDictionary. Remove the setting for the ValueName property.";
+       public const string InvalidCollectionDataContract = "Type '{0}' with CollectionDataContractAttribute attribute is an invalid collection type since it";
+       public const string InvalidCollectionType = "Type '{0}' is an invalid collection type since it";
+       public const string InvalidDataContractName = "Type '{0}' cannot have DataContractAttribute attribute Name set to null or empty string.";
+       public const string InvalidDataContractNamespace = "Type '{0}' cannot have DataContractAttribute attribute Namespace set to null.";
+       public const string InvalidDataMemberName = "Member '{0}' in type '{1}' cannot have DataMemberAttribute attribute Name set to null or empty string.";
+       public const string InvalidEnumMemberValue = "'{0}' in type '{1}' cannot have EnumMemberAttribute attribute Value set to null or empty string.";
+       public const string InvalidEnumValueOnRead = "Invalid enum value '{0}' cannot be deserialized into type '{1}'. Ensure that the necessary enum values are present and are marked with EnumMemberAttribute attribute if the type has DataContractAttribute attribute.";
+       public const string InvalidEnumValueOnWrite = "Enum value '{0}' is invalid for type '{1}' and cannot be serialized. Ensure that the necessary enum values are present and are marked with EnumMemberAttribute attribute if the type has DataContractAttribute attribute.";
+       public const string InvalidGetSchemaMethod = "Type '{0}' cannot have MethodName on XmlSchemaProviderAttribute attribute set to null or empty string.";
+       public const string InvalidGlobalDataContractNamespace = "CLR namespace '{0}' cannot have ContractNamespace set to null.";
+       public const string InvalidMember = "Member '{0}.{1}' cannot be serialized since it is neither a field nor a property, and therefore cannot be marked with the DataMemberAttribute attribute. Remove the DataMemberAttribute attribute from the '{1}' member.";
+       public const string InvalidNonNullReturnValueByIsAny = "Method '{0}.{1}()' returns a non-null value. The return value must be null since IsAny=true.";
+       public const string InvalidPrimitiveType = "Type '{0}' is not a valid serializable type.";
+       public const string InvalidReturnTypeOnGetSchemaMethod = "Method '{0}.{1}()' returns '{2}'. The return type must be compatible with '{3}'.";
+       public const string InvalidSizeDefinition = "Invalid Size '{0}'. Must be non-negative integer.";
+       public const string InvalidXmlDataContractName = "XML data contract Name for type '{0}' cannot be set to null or empty string.";
+       public const string InvalidXsIdDefinition = "Invalid Id '{0}'. Must not be null or empty.";
+       public const string InvalidXsRefDefinition = "Invalid Ref '{0}'. Must not be null or empty.";
+       public const string IsAnyCannotBeNull = "A null value cannot be serialized at the top level for IXmlSerializable root type '{0}' since its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
+       public const string IsAnyCannotBeSerializedAsDerivedType = "An object of type '{0}' cannot be serialized at the top level for IXmlSerializable root type '{1}' since its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
+       public const string IsAnyCannotHaveXmlRoot = "Type '{0}' cannot specify an XmlRootAttribute attribute because its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
+       public const string IsNotAssignableFrom = "An internal error has occurred. '{0}' is not assignable from '{1}' - error generating code for serialization.";
+       public const string IsRequiredDataMemberOnIsReferenceDataContractType = "'{0}.{1}' has the IsRequired setting of '{2}. However, '{0}' has the IsReference setting of '{2}', because either it is set explicitly, or it is derived from a base class. Set IsRequired on '{0}.{1}' to false, or disable IsReference on '{0}'.";
+       public const string IXmlSerializableCannotHaveCollectionDataContract = "Type '{0}' cannot be IXmlSerializable and have CollectionDataContractAttribute attribute.";
+       public const string IXmlSerializableCannotHaveDataContract = "Type '{0}' cannot be IXmlSerializable and have DataContractAttribute attribute.";
+       public const string IXmlSerializableIllegalOperation = "This method cannot be called from IXmlSerializable implementations.";
+       public const string IXmlSerializableMissingEndElements = "IXmlSerializable.WriteXml method of type '{0}' did not close all open tags. Verify that the IXmlSerializable implementation is correct.";
+       public const string IXmlSerializableMustHaveDefaultConstructor = "IXmlSerializable Type '{0}' must have default constructor.";
+       public const string IXmlSerializableWritePastSubTree = "IXmlSerializable.WriteXml method of type '{0}' attempted to close too many tags.  Verify that the IXmlSerializable implementation is correct.";
+       public const string KnownTypeAttributeEmptyString = "Method name specified by KnownTypeAttribute attribute on type '{0}' cannot be the empty string.";
+       public const string KnownTypeAttributeUnknownMethod = "KnownTypeAttribute attribute on type '{1}' specifies a method named '{0}' to provide known types. Static method '{0}()' was not found on this type. Ensure that the method exists and is marked as static.";
+       public const string KnownTypeAttributeReturnType = "KnownTypeAttribute attribute on type '{0}' specifies a method named '{1}' to provide known types. The return type of this method is invalid because it is not assignable to IEnumerable<Type>. Ensure that the method exists and has a valid signature.";
+       public const string KnownTypeAttributeOneScheme = "Type '{0}': If a KnownTypeAttribute attribute specifies a method it must be the only KnownTypeAttribute attribute on that type.";
+       public const string KnownTypeAttributeNoType = "KnownTypeAttribute attribute on type '{0}' contains no Type.";
+       public const string KnownTypeConfigClosedGenericDeclared = "Declared type '{0}' in config cannot be a closed or partial generic type.";
+       public const string KnownTypeAttributeValidMethodTypes = "Method specified by KnownTypeAttribute attribute on type '{0}' does not expose valid types.";
+       public const string KnownTypeAttributeNoData = "KnownTypeAttribute attribute on type '{0}' contains no data.";
+       public const string KnownTypeAttributeMethodNull = "Method specified by KnownTypeAttribute attribute on type '{0}' returned null.";
+       public const string MaxArrayLengthExceeded = "The maximum array length ({0}) has been exceeded while reading XML data for array of type '{1}'.";
+       public const string MissingGetSchemaMethod = "Type '{0}' does not have a static method '{1}' that takes a parameter of type 'System.Xml.Schema.XmlSchemaSet' as specified by the XmlSchemaProviderAttribute attribute.";
+       public const string MultipleIdDefinition = "Invalid XML encountered. The same Id value '{0}' is defined more than once. Multiple objects cannot be deserialized using the same Id.";
+       public const string NoConversionPossibleTo = "An internal error has occurred. No conversion is possible to '{0}' - error generating code for serialization.";
+       public const string NoGetMethodForProperty = "No get method for property '{1}' in type '{0}'.";
+       public const string NoSetMethodForProperty = "No set method for property '{1}' in type '{0}'.";
+       public const string NullKnownType = "One of the known types provided to the serializer via '{0}' argument was invalid because it was null. All known types specified must be non-null values.";
+       public const string NullValueReturnedForGetOnlyCollection = "The get-only collection of type '{0}' returned a null value.  The input stream contains collection items which cannot be added if the instance is null.  Consider initializing the collection either in the constructor of the the object or in the getter.";
+       public const string ObjectTableOverflow = "An internal error has occurred. Object table overflow. This could be caused by serializing or deserializing extremely large object graphs.";
+       public const string OrderCannotBeNegative = "Property 'Order' in DataMemberAttribute attribute cannot be a negative number.";
+       public const string ParameterCountMismatch = "Invalid number of parameters to call method '{0}'. Expected '{1}' parameters, but '{2}' were provided.";
+       public const string PartialTrustCollectionContractAddMethodNotPublic = "The collection data contract type '{0}' cannot be deserialized because the method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustCollectionContractNoPublicConstructor = "The collection data contract type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustCollectionContractTypeNotPublic = "The collection data contract type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractOnSerializingNotPublic = "The data contract type '{0}' cannot be serialized because the OnSerializing method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractOnSerializedNotPublic = "The data contract type '{0}' cannot be serialized because the OnSerialized method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractOnDeserializingNotPublic = "The data contract type '{0}' cannot be deserialized because the OnDeserializing method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractOnDeserializedNotPublic = "The data contract type '{0}' cannot be deserialized because the OnDeserialized method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractFieldGetNotPublic = "The data contract type '{0}' cannot be serialized because the member '{1}' is not public. Making the member public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractFieldSetNotPublic = "The data contract type '{0}' cannot be deserialized because the member '{1}' is not public. Making the member public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractPropertyGetNotPublic = "The data contract type '{0}' cannot be serialized because the property '{1}' does not have a public getter. Adding a public getter will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractPropertySetNotPublic = "The data contract type '{0}' cannot be deserialized because the property '{1}' does not have a public setter. Adding a public setter will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustDataContractTypeNotPublic = "The data contract type '{0}' is not serializable because it is not public. Making the type public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustNonAttributedSerializableTypeNoPublicConstructor = "The type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustIXmlSerializableTypeNotPublic = "The IXmlSerializable type '{0}' is not serializable in partial trust because it is not public. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string PartialTrustIXmlSerialzableNoPublicConstructor = "The IXmlSerializable type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
+       public const string NonAttributedSerializableTypesMustHaveDefaultConstructor = "The Type '{0}' must have a parameterless constructor.";
+       public const string AttributedTypesCannotInheritFromNonAttributedSerializableTypes = "Type '{0}' cannot inherit from a type that is not marked with DataContractAttribute or SerializableAttribute.  Consider marking the base type '{1}' with DataContractAttribute or SerializableAttribute, or removing them from the derived type.";
+       public const string GetOnlyCollectionsNotSupported = "Get-only collection properties are not supported.  Consider adding a public setter to property '{0}.{1}' or marking the it with the IgnoreDataMemberAttribute.";
+       public const string QuotaMustBePositive = "Quota must be a positive value.";
+       public const string QuotaIsReadOnly = "The '{0}' quota is readonly.";
+       public const string QuotaCopyReadOnly = "Cannot copy XmlDictionaryReaderQuotas. Target is readonly.";
+       public const string RequiredMemberMustBeEmitted = "Member {0} in type {1} cannot be serialized. This exception is usually caused by trying to use a null value where a null value is not allowed. The '{0}' member is set to its default value (usually null or zero). The member's EmitDefault setting is 'false', indicating that the member should not be serialized. However, the member's IsRequired setting is 'true', indicating that it must be serialized. This conflict cannot be resolved.  Consider setting '{0}' to a non-default value. Alternatively, you can change the EmitDefaultValue property on the DataMemberAttribute attribute to true, or changing the IsRequired property to false.";
+       public const string ResolveTypeReturnedFalse = "An object of type '{0}' which derives from DataContractResolver returned false from its TryResolveType method when attempting to resolve the name for an object of type '{1}', indicating that the resolution failed. Change the TryResolveType implementation to return true.";
+       public const string ResolveTypeReturnedNull = "An object of type '{0}' which derives from DataContractResolver returned a null typeName or typeNamespace but not both from its TryResolveType method when attempting to resolve the name for an object of type '{1}'. Change the TryResolveType implementation to return non-null values, or to return null values for both typeName and typeNamespace in order to serialize as the declared type.";
+       public const string SupportForMultidimensionalArraysNotPresent = "Multi-dimensional arrays are not supported.";
+       public const string TooManyCollectionContracts = "Type '{0}' has more than one CollectionDataContractAttribute attribute.";
+       public const string TooManyDataContracts = "Type '{0}' has more than one DataContractAttribute attribute.";
+       public const string TooManyDataMembers = "Member '{0}.{1}' has more than one DataMemberAttribute attribute.";
+       public const string TooManyEnumMembers = "Member '{0}.{1}' has more than one EnumMemberAttribute attribute.";
+       public const string TooManyIgnoreDataMemberAttributes = "Member '{0}.{1}' has more than one IgnoreDataMemberAttribute attribute.";
+       public const string TypeMustBeConcrete = "Error while getting known types for Type '{0}'. The type must not be an open or partial generic class.";
+       public const string TypeNotSerializable = "Type '{0}' cannot be serialized. Consider marking it with the DataContractAttribute attribute, and marking all of its members you want serialized with the DataMemberAttribute attribute. Alternatively, you can ensure that the type is public and has a parameterless constructor - all public members of the type will then be serialized, and no attributes will be required.";
+       public const string UnexpectedContractType = "An internal error has occurred. Unexpected contract type '{0}' for type '{1}' encountered.";
+       public const string UnexpectedElementExpectingElements = "'{0}' '{1}' from namespace '{2}' is not expected. Expecting element '{3}'.";
+       public const string UnexpectedEndOfFile = "Unexpected end of file.";
+       public const string UnknownConstantType = "Unrecognized constant type '{0}'.";
+       public const string UnsupportedIDictionaryAsDataMemberType = "Cannot deserialize one of the DataMember because it is an IDictionary. Use IDictionary<K,V> instead.";
+       public const string ValueMustBeNonNegative = "The value of this argument must be non-negative.";
+       public const string ValueTypeCannotBeNull = "ValueType '{0}' cannot be null.";
+       public const string ValueTypeCannotHaveBaseType = "Data contract '{0}' from namespace '{1}' is a value type and cannot have base contract '{2}' from namespace '{3}'.";
+       public const string ValueTypeCannotHaveId = "ValueType '{0}' cannot have id.";
+       public const string ValueTypeCannotHaveIsReference = "Value type '{0}' cannot have the IsReference setting of '{1}'. Either change the setting to '{2}', or remove it completely.";
+       public const string ValueTypeCannotHaveRef = "ValueType '{0}' cannot have ref to another object.";
+       public const string XmlElementAttributes = "Only Element nodes have attributes.";
+       public const string XmlForObjectCannotHaveContent = "Element {0} from namespace {1} cannot have child contents to be deserialized as an object. Please use XElement to deserialize this pattern of XML.";
+       public const string XmlInvalidConversion = "The value '{0}' cannot be parsed as the type '{1}'.";
+       public const string XmlInvalidConversionWithoutValue = "The value cannot be parsed as the type '{0}'.";
+       public const string XmlStartElementExpected = "Start element expected. Found {0}.";
+       public const string XmlWriterMustBeInElement = "WriteState '{0}' not valid. Caller must write start element before serializing in contentOnly mode.";
+       public const string OffsetExceedsBufferSize = "The specified offset exceeds the buffer size ({0} bytes).";
+       public const string SizeExceedsRemainingBufferSpace = "The specified size exceeds the remaining buffer space ({0} bytes).";
+       public const string ValueMustBeInRange = "The value of this argument must fall within the range {0} to {1}.";
+       public const string XmlArrayTooSmallOutput = "Array too small.  Must be able to hold at least {0}.";
+       public const string XmlInvalidBase64Length = "Base64 sequence length ({0}) not valid. Must be a multiple of 4.";
+       public const string XmlInvalidBase64Sequence = "The characters '{0}' at offset {1} are not a valid Base64 sequence.";
+       public const string XmlInvalidBinHexLength = "BinHex sequence length ({0}) not valid. Must be a multiple of 2.";
+       public const string XmlInvalidBinHexSequence = "The characters '{0}' at offset {1} are not a valid BinHex sequence.";
+       public const string XmlInvalidHighSurrogate = "High surrogate char '0x{0}' not valid. High surrogate chars range from 0xD800 to 0xDBFF.";
+       public const string XmlInvalidLowSurrogate = "Low surrogate char '0x{0}' not valid. Low surrogate chars range from 0xDC00 to 0xDFFF.";
+       public const string XmlInvalidSurrogate = "Surrogate char '0x{0}' not valid. Surrogate chars range from 0x10000 to 0x10FFFF.";
+       public const string CombinedPrefixNSLength = "The combined length of the prefix and namespace must not be greater than {0}.";
+       public const string InvalidInclusivePrefixListCollection = "The inclusive namespace prefix collection cannot contain null as one of the items.";
+       public const string InvalidLocalNameEmpty = "The empty string is not a valid local name.";
+       public const string XmlArrayTooSmall = "Array too small.";
+       public const string XmlArrayTooSmallInput = "Array too small.  Length of available data must be at least {0}.";
+       public const string XmlBadBOM = "Unrecognized Byte Order Mark.";
+       public const string XmlBase64DataExpected = "Base64 encoded data expected. Found {0}.";
+       public const string XmlCDATAInvalidAtTopLevel = "CData elements not valid at top level of an XML document.";
+       public const string XmlCloseCData = "']]>' not valid in text node content.";
+       public const string XmlConversionOverflow = "The value '{0}' cannot be represented with the type '{1}'.";
+       public const string XmlDeclarationRequired = "An XML declaration with an encoding is required for all non-UTF8 documents.";
+       public const string XmlDeclMissingVersion = "Version not found in XML declaration.";
+       public const string XmlDeclMissing = "An XML declaration is required for all non-UTF8 documents.";
+       public const string XmlDeclNotFirst = "No characters can appear before the XML declaration.";
+       public const string XmlDictionaryStringIDRange = "XmlDictionaryString IDs must be in the range from {0} to {1}.";
+       public const string XmlDictionaryStringIDUndefinedSession = "XmlDictionaryString ID {0} not defined in the XmlBinaryReaderSession.";
+       public const string XmlDictionaryStringIDUndefinedStatic = "XmlDictionaryString ID {0} not defined in the static dictionary.";
+       public const string XmlDuplicateAttribute = "Duplicate attribute found. Both '{0}' and '{1}' are from the namespace '{2}'.";
+       public const string XmlEmptyNamespaceRequiresNullPrefix = "The empty namespace requires a null or empty prefix.";
+       public const string XmlEncodingMismatch = "The encoding in the declaration '{0}' does not match the encoding of the document '{1}'.";
+       public const string XmlEncodingNotSupported = "XML encoding not supported.";
+       public const string XmlEndElementExpected = "End element '{0}' from namespace '{1}' expected. Found {2}.";
+       public const string XmlEndElementNoOpenNodes = "No corresponding start element is open.";
+       public const string XmlExpectedEncoding = "The expected encoding '{0}' does not match the actual encoding '{1}'.";
+       public const string XmlFoundCData = "cdata '{0}'";
+       public const string XmlFoundComment = "comment '{0}'";
+       public const string XmlFoundElement = "element '{0}' from namespace '{1}'";
+       public const string XmlFoundEndElement = "end element '{0}' from namespace '{1}'";
+       public const string XmlFoundEndOfFile = "end of file";
+       public const string XmlFoundNodeType = "node {0}";
+       public const string XmlFoundText = "text '{0}'";
+       public const string XmlFullStartElementExpected = "Non-empty start element expected. Found {0}.";
+       public const string XmlFullStartElementLocalNameNsExpected = "Non-empty start element '{0}' from namespace '{1}' expected. Found {2}.";
+       public const string XmlFullStartElementNameExpected = "Non-empty start element '{0}' expected. Found {1}.";
+       public const string XmlIDDefined = "ID already defined.";
+       public const string XmlKeyAlreadyExists = "The specified key already exists in the dictionary.";
+       public const string XmlIllegalOutsideRoot = "Text cannot be written outside the root element.";
+       public const string XmlInvalidBytes = "Invalid byte encoding.";
+       public const string XmlInvalidCharRef = "Character reference not valid.";
+       public const string XmlInvalidCommentChars = "XML comments cannot contain '--' or end with '-'.";
+       public const string XmlInvalidDeclaration = "XML declaration can only be written at the beginning of the document.";
+       public const string XmlInvalidDepth = "Cannot call '{0}' while Depth is '{1}'.";
+       public const string XmlInvalidEncoding = "XML encoding must be 'UTF-8'.";
+       public const string XmlInvalidFFFE = "Characters with hexadecimal values 0xFFFE and 0xFFFF are not valid.";
+       public const string XmlInvalidFormat = "The input source is not correctly formatted.";
+       public const string XmlInvalidID = "ID must be >= 0.";
+       public const string XmlInvalidOperation = "The reader cannot be advanced.";
+       public const string XmlInvalidPrefixState = "A prefix cannot be defined while WriteState is '{0}'.";
+       public const string XmlInvalidQualifiedName = "Expected XML qualified name. Found '{0}'.";
+       public const string XmlInvalidRootData = "The data at the root level is invalid.";
+       public const string XmlInvalidStandalone = "'standalone' value in declaration must be 'yes' or 'no'.";
+       public const string XmlInvalidStream = "Stream returned by IStreamProvider cannot be null.";
+       public const string XmlInvalidUniqueId = "UniqueId cannot be zero length.";
+       public const string XmlInvalidUTF8Bytes = "'{0}' contains invalid UTF8 bytes.";
+       public const string XmlInvalidVersion = "XML version must be '1.0'.";
+       public const string XmlInvalidWriteState = "'{0}' cannot be called while WriteState is '{1}'.";
+       public const string XmlInvalidXmlByte = "The byte 0x{0} is not valid at this location.";
+       public const string XmlInvalidXmlSpace = "'{0}' is not a valid xml:space value. Valid values are 'default' and 'preserve'.";
+       public const string XmlLineInfo = "Line {0}, position {1}.";
+       public const string XmlMalformedDecl = "Malformed XML declaration.";
+       public const string XmlMaxArrayLengthExceeded = "The maximum array length quota ({0}) has been exceeded while reading XML data. This quota may be increased by changing the MaxArrayLength property on the XmlDictionaryReaderQuotas object used when creating the XML reader.";
+       public const string XmlMaxNameTableCharCountExceeded = "The maximum nametable character count quota ({0}) has been exceeded while reading XML data. The nametable is a data structure used to store strings encountered during XML processing - long XML documents with non-repeating element names, attribute names and attribute values may trigger this quota. This quota may be increased by changing the MaxNameTableCharCount property on the XmlDictionaryReaderQuotas object used when creating the XML reader.";
+       public const string XmlMethodNotSupported = "This XmlWriter implementation does not support the '{0}' method.";
+       public const string XmlMissingLowSurrogate = "The surrogate pair is invalid. Missing a low surrogate character.";
+       public const string XmlMultipleRootElements = "There are multiple root elements.";
+       public const string XmlNamespaceNotFound = "The namespace '{0}' is not defined.";
+       public const string XmlNestedArraysNotSupported = "Nested arrays are not supported.";
+       public const string XmlNoRootElement = "The document does not have a root element.";
+       public const string XmlOnlyOneRoot = "Only one root element is permitted per document.";
+       public const string XmlOnlyWhitespace = "Only white space characters can be written with this method.";
+       public const string XmlOnlySingleValue = "Only a single typed value may be written inside an attribute or content.";
+       public const string XmlPrefixBoundToNamespace = "The prefix '{0}' is bound to the namespace '{1}' and cannot be changed to '{2}'.";
+       public const string XmlProcessingInstructionNotSupported = "Processing instructions (other than the XML declaration) and DTDs are not supported.";
+       public const string XmlReservedPrefix = "Prefixes beginning with \"xml\" (regardless of casing) are reserved for use by XML.";
+       public const string XmlSpaceBetweenAttributes = "Whitespace must appear between attributes.";
+       public const string XmlSpecificBindingNamespace = "The namespace '{1}' can only be bound to the prefix '{0}'.";
+       public const string XmlSpecificBindingPrefix = "The prefix '{0}' can only be bound to the namespace '{1}'.";
+       public const string XmlStartElementLocalNameNsExpected = "Start element '{0}' from namespace '{1}' expected. Found {2}.";
+       public const string XmlStartElementNameExpected = "Start element '{0}' expected. Found {1}.";
+       public const string XmlTagMismatch = "Start element '{0}' does not match end element '{1}'.";
+       public const string XmlTokenExpected = "The token '{0}' was expected but found '{1}'.";
+       public const string XmlUndefinedPrefix = "The prefix '{0}' is not defined.";
+       public const string XmlUnexpectedEndElement = "No matching start tag for end element.";
+       public const string XmlUnexpectedEndOfFile = "Unexpected end of file. Following elements are not closed: {0}.";
+       public const string XmlWriterClosed = "The XmlWriter is closed.";
+       public const string Xml_InvalidNmToken = "Invalid NmToken value '{0}'.";
 }
-}
-
-/*
-namespace System.Text
-{
-       static partial class SR
-       {
-        internal static string GetString(string name, params object[] args)
-        {
-                return GetString (CultureInfo.InvariantCulture, name, args);
-        }
-
-        internal static string GetString(CultureInfo culture, string name, params object[] args) {
-                return string.Format (culture, name, args);
-        }
-
-        internal static string GetString(string name)
-        {
-                return name;
-        }
-
-        internal static string GetString(CultureInfo culture, string name)
-        {
-                return name;
-        }
-}
-}
-
-namespace System.Xml
-{
-       static partial class SR
-       {
-        internal static string GetString(string name, params object[] args)
-        {
-                return GetString (CultureInfo.InvariantCulture, name, args);
-        }
-
-        internal static string GetString(CultureInfo culture, string name, params object[] args) {
-                return string.Format (culture, name, args);
-        }
-
-        internal static string GetString(string name)
-        {
-                return name;
-        }
-
-        internal static string GetString(CultureInfo culture, string name)
-        {
-                return name;
-        }
-}
-}
-*/
-#endregion
-
-
-#region "retrieved string resources"
-
-namespace System.Runtime.Serialization
-{
-       static partial class SR {
-
-
-public const string ArrayExceededSize = @"Array length '{0}' provided by the get-only collection of type '{1}' is less than the number of array elements found in the input stream.  Consider increasing the length of the array.";
-public const string ArrayExceededSizeAttribute = @"Array length '{0}' provided by Size attribute is not equal to the number of array elements '{1}' from namespace '{2}' found.";
-public const string ArrayTypeIsNotSupported = @"An internal error has occurred. '{0}[]' is not supported when generating code for serialization.";
-public const string CannotDeserializeRefAtTopLevel = @"Cannot deserialize since root element references unrecognized object with id '{0}'.";
-public const string CannotLoadMemberType = @"Cannot load member type '{0}'.";
-public const string CannotSerializeObjectWithCycles = @"Object graph for type '{0}' contains cycles and cannot be serialized if references are not tracked. Consider using the DataContractAttribute with the IsReference property set to true.";
-public const string CanOnlyStoreIntoArgOrLocGot0 = @"An internal error has occurred. Data can only be stored into ArgBuilder or LocalBuilder. Got: {0}.";
-public const string CharIsInvalidPrimitive = @"An internal error has occurred. Char is not a valid schema primitive and should be treated as int in DataContract.";
-public const string CallbackMustReturnVoid = @"Serialization Callback '{1}' in type '{0}' must return void. ";
-public const string CallbackParameterInvalid = @"Serialization Callback '{1}' in type '{0}' must have a single parameter of type '{2}'. ";
-public const string CallbacksCannotBeVirtualMethods = @"Virtual Method '{0}' of type '{1}' cannot be marked with '{2}' attribute. ";
-public const string CollectionMustHaveAddMethod = @"Collection type '{0}' does not have a valid Add method.";
-public const string CollectionMustHaveGetEnumeratorMethod = @"Collection type '{0}' does not have a valid GetEnumerator method.";
-public const string CollectionMustHaveItemType = @"Collection type '{0}' must have a non-null item type.";
-public const string CollectionTypeCannotBeBuiltIn = @"{0} is a built-in type and cannot be a collection.";
-public const string CollectionTypeCannotHaveDataContract = @"{0} has DataContractAttribute attribute.";
-public const string CollectionTypeDoesNotHaveAddMethod = @"{0} does not have a valid Add method with parameter of type '{1}'.";
-public const string CollectionTypeDoesNotHaveDefaultCtor = @"{0} does not have a default constructor.";
-public const string CollectionTypeHasMultipleDefinitionsOfInterface = @"{0} has multiple definitions of interface '{1}'.";
-public const string CollectionTypeIsNotIEnumerable = @"{0} does not implement IEnumerable interface.";
-public const string DataContractCacheOverflow = @"An internal error has occurred. DataContract cache overflow.";
-public const string DataContractNamespaceAlreadySet = @"ContractNamespaceAttribute attribute maps CLR namespace '{2}' to multiple data contract namespaces '{0}' and '{1}'. You can map a CLR namespace to only one data contract namespace.";
-public const string DataContractNamespaceIsNotValid = @"DataContract namespace '{0}' is not a valid URI.";
-public const string DataContractNamespaceReserved = @"DataContract namespace '{0}' cannot be specified since it is reserved.";
-public const string DataMemberOnEnumField = @"Member '{0}.{1}' has DataMemberAttribute attribute. Use EnumMemberAttribute attribute instead.";
-public const string DcTypeNotFoundOnDeserialize = @"Element '{2}:{3}' contains data of the '{0}:{1}' data contract. The deserializer has no knowledge of any type that maps to this contract. Add the type corresponding to '{1}' to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding it to the list of known types passed to DataContractSerializer.";
-public const string DcTypeNotFoundOnSerialize = @"Type '{0}' with data contract name '{1}:{2}' is not expected. Add any types not known statically to the list of known types - for example, by using the KnownTypeAttribute attribute or by adding them to the list of known types passed to DataContractSerializer.";
-public const string DcTypeNotResolvedOnDeserialize = @"Element '{2}:{3}' contains data from a type that maps to the name '{0}:{1}'. The deserializer has no knowledge of any type that maps to this name. Consider changing the implementation of the ResolveName method on your DataContractResolver to return a non-null value for name '{1}' and namespace '{0}'.";
-public const string DeserializedObjectWithIdNotFound = @"Deserialized object with reference id '{0}' not found in stream.";
-public const string DupContractInKnownTypes = @"Type '{0}' cannot be added to list of known types since another type '{1}' with the same data contract name '{2}:{3}' is already present.";
-public const string DupKeyValueName = @"The collection data contract type '{0}' specifies the same value '{1}' for both the KeyName and the ValueName properties. This is not allowed. Consider changing either the KeyName or the ValueName property.";
-public const string DupEnumMemberValue = @"Type '{2}' contains two members '{0}' 'and '{1}' with the same name '{3}'. Multiple members with the same name in one type are not supported. Consider changing one of the member names using EnumMemberAttribute attribute.";
-public const string DupMemberName = @"Type '{2}' contains two members '{0}' 'and '{1}' with the same data member name '{3}'. Multiple members with the same name in one type are not supported. Consider changing one of the member names using DataMemberAttribute attribute.";
-public const string DuplicateAttribute = @"Invalid Callback. Method '{3}' in type '{2}' has both '{0}' and '{1}'. ";
-public const string DuplicateCallback = @"Invalid attribute. Both '{0}' and '{1}' in type '{2}' have '{3}'. ";
-public const string EncounteredWithNameNamespace = @"{0}. Encountered '{1}'  with name '{2}', namespace '{3}'.";
-public const string EnumTypeCannotHaveIsReference = @"Enum type '{0}' cannot have the IsReference setting of '{1}'. Either change the setting to '{2}', or remove it completely.";
-public const string ErrorDeserializing = @"There was an error deserializing the object {0}. {1}";
-public const string ErrorInLine = @"Error in line {0} position {1}.";
-public const string ErrorIsStartObject = @"There was an error checking start element of object {0}. {1}";
-public const string ErrorSerializing = @"There was an error serializing the object {0}. {1}";
-public const string ErrorTypeInfo = @"of type {0}";
-public const string ErrorWriteEndObject = @"There was an error writing end element of object {0}. {1}";
-public const string ErrorWriteStartObject = @"There was an error writing start element of object {0}. {1}";
-public const string ExceededMaxItemsQuota = @"Maximum number of items that can be serialized or deserialized in an object graph is '{0}'.";
-public const string ExpectingElement = @"Expecting element '{1}' from namespace '{0}'.";
-public const string ExpectingElementAtDeserialize = @"Expecting state '{0}' when ReadObject is called.";
-public const string ExpectingEnd = @"Expecting End'{0}'.";
-public const string ExpectingState = @"Expecting state '{0}'.";
-public const string GenericNameBraceMismatch = @"The data contract name '{0}' for type '{1}' has a curly brace '{{' that is not matched with a closing curly brace. Curly braces have special meaning in data contract names - they are used to customize the naming of data contracts for generic types.";
-public const string GenericParameterNotValid = @"In the data contract name for type '{1}', there are curly braces with '{0}' inside, which is an invalid value. Curly braces have special meaning in data contract names - they are used to customize the naming of data contracts for generic types. Based on the number of generic parameters this type has, the contents of the curly braces must either be a number between 0 and '{2}' to insert the name of the generic parameter at that index or the '#' symbol to insert a digest of the generic parameter namespaces.";
-public const string InconsistentIsReference = @"The IsReference setting for type '{0}' is '{1}', but the same setting for its parent class '{2}' is '{3}'. Derived types must have the same value for IsReference as the base type. Change the setting on type '{0}' to '{3}', or on type '{2}' to '{1}', or do not set IsReference explicitly.";
-public const string IndexedPropertyCannotBeSerialized = @"Property '{1}' in type '{0}' cannot be serialized because serialization of indexed properties is not supported.";
-public const string InterfaceTypeCannotBeCreated = @"Interface type '{0}' cannot be created. Consider replacing with a non-interface serializable type.";
-public const string InvalidCollectionContractItemName = @"Type '{0}' cannot have CollectionDataContractAttribute attribute ItemName set to null or empty string.";
-public const string InvalidCollectionContractKeyName = @"Type '{0}' cannot have CollectionDataContractAttribute attribute KeyName set to null or empty string.";
-public const string InvalidCollectionContractKeyNoDictionary = @"The collection data contract type '{0}' specifies '{1}' for the KeyName property. This is not allowed since the type is not IDictionary. Remove the setting for the KeyName property.";
-public const string InvalidCollectionContractName = @"Type '{0}' cannot have CollectionDataContractAttribute attribute Name set to null or empty string.";
-public const string InvalidCollectionContractNamespace = @"Type '{0}' cannot have CollectionDataContractAttribute attribute Namespace set to null.";
-public const string InvalidCollectionContractValueName = @"Type '{0}' cannot have CollectionDataContractAttribute attribute ValueName set to null or empty string.";
-public const string InvalidCollectionContractValueNoDictionary = @"The collection data contract type '{0}' specifies '{1}' for the ValueName property. This is not allowed since the type is not IDictionary. Remove the setting for the ValueName property.";
-public const string InvalidCollectionDataContract = @"Type '{0}' with CollectionDataContractAttribute attribute is an invalid collection type since it";
-public const string InvalidCollectionType = @"Type '{0}' is an invalid collection type since it";
-public const string InvalidDataContractName = @"Type '{0}' cannot have DataContractAttribute attribute Name set to null or empty string.";
-public const string InvalidDataContractNamespace = @"Type '{0}' cannot have DataContractAttribute attribute Namespace set to null.";
-public const string InvalidDataMemberName = @"Member '{0}' in type '{1}' cannot have DataMemberAttribute attribute Name set to null or empty string.";
-public const string InvalidEnumMemberValue = @"'{0}' in type '{1}' cannot have EnumMemberAttribute attribute Value set to null or empty string.";
-public const string InvalidEnumValueOnRead = @"Invalid enum value '{0}' cannot be deserialized into type '{1}'. Ensure that the necessary enum values are present and are marked with EnumMemberAttribute attribute if the type has DataContractAttribute attribute.";
-public const string InvalidEnumValueOnWrite = @"Enum value '{0}' is invalid for type '{1}' and cannot be serialized. Ensure that the necessary enum values are present and are marked with EnumMemberAttribute attribute if the type has DataContractAttribute attribute.";
-public const string InvalidGetSchemaMethod = @"Type '{0}' cannot have MethodName on XmlSchemaProviderAttribute attribute set to null or empty string. ";
-public const string InvalidGlobalDataContractNamespace = @"CLR namespace '{0}' cannot have ContractNamespace set to null.";
-public const string InvalidMember = @"Member '{0}.{1}' cannot be serialized since it is neither a field nor a property, and therefore cannot be marked with the DataMemberAttribute attribute. Remove the DataMemberAttribute attribute from the '{1}' member.";
-public const string InvalidNonNullReturnValueByIsAny = @"Method '{0}.{1}()' returns a non-null value. The return value must be null since IsAny=true.";
-public const string InvalidPrimitiveType = @"Type '{0}' is not a valid serializable type.";
-public const string InvalidReturnTypeOnGetSchemaMethod = @"Method '{0}.{1}()' returns '{2}'. The return type must be compatible with '{3}'.";
-public const string InvalidSizeDefinition = @"Invalid Size '{0}'. Must be non-negative integer.";
-public const string InvalidXmlDataContractName = @"XML data contract Name for type '{0}' cannot be set to null or empty string.";
-public const string InvalidXsIdDefinition = @"Invalid Id '{0}'. Must not be null or empty.";
-public const string InvalidXsRefDefinition = @"Invalid Ref '{0}'. Must not be null or empty.";
-public const string IsAnyCannotBeNull = @"A null value cannot be serialized at the top level for IXmlSerializable root type '{0}' since its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
-public const string IsAnyCannotBeSerializedAsDerivedType = @"An object of type '{0}' cannot be serialized at the top level for IXmlSerializable root type '{1}' since its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
-public const string IsAnyCannotHaveXmlRoot = @"Type '{0}' cannot specify an XmlRootAttribute attribute because its IsAny setting is 'true'. This type must write all its contents including the root element. Verify that the IXmlSerializable implementation is correct.";
-public const string IsNotAssignableFrom = @"An internal error has occurred. '{0}' is not assignable from '{1}' - error generating code for serialization.";
-public const string IsRequiredDataMemberOnIsReferenceDataContractType = @"'{0}.{1}' has the IsRequired setting of '{2}. However, '{0}' has the IsReference setting of '{2}', because either it is set explicitly, or it is derived from a base class. Set IsRequired on '{0}.{1}' to false, or disable IsReference on '{0}'.";
-public const string IXmlSerializableCannotHaveCollectionDataContract = @"Type '{0}' cannot be IXmlSerializable and have CollectionDataContractAttribute attribute.";
-public const string IXmlSerializableCannotHaveDataContract = @"Type '{0}' cannot be IXmlSerializable and have DataContractAttribute attribute.";
-public const string IXmlSerializableIllegalOperation = @"This method cannot be called from IXmlSerializable implementations.";
-public const string IXmlSerializableMissingEndElements = @"IXmlSerializable.WriteXml method of type '{0}' did not close all open tags. Verify that the IXmlSerializable implementation is correct.";
-public const string IXmlSerializableMustHaveDefaultConstructor = @"IXmlSerializable Type '{0}' must have default constructor.";
-public const string IXmlSerializableWritePastSubTree = @"IXmlSerializable.WriteXml method of type '{0}' attempted to close too many tags.  Verify that the IXmlSerializable implementation is correct.";
-public const string KnownTypeAttributeEmptyString = @"Method name specified by KnownTypeAttribute attribute on type '{0}' cannot be the empty string.";
-public const string KnownTypeAttributeUnknownMethod = @"KnownTypeAttribute attribute on type '{1}' specifies a method named '{0}' to provide known types. Static method '{0}()' was not found on this type. Ensure that the method exists and is marked as static.";
-public const string KnownTypeAttributeReturnType = @"KnownTypeAttribute attribute on type '{0}' specifies a method named '{1}' to provide known types. The return type of this method is invalid because it is not assignable to IEnumerable<Type>. Ensure that the method exists and has a valid signature.";
-public const string KnownTypeAttributeOneScheme = @"Type '{0}': If a KnownTypeAttribute attribute specifies a method it must be the only KnownTypeAttribute attribute on that type.";
-public const string KnownTypeAttributeNoType = @"KnownTypeAttribute attribute on type '{0}' contains no Type.";
-public const string KnownTypeConfigClosedGenericDeclared = @"Declared type '{0}' in config cannot be a closed or partial generic type.";
-public const string KnownTypeAttributeValidMethodTypes = @"Method specified by KnownTypeAttribute attribute on type '{0}' does not expose valid types.";
-public const string KnownTypeAttributeNoData = @"KnownTypeAttribute attribute on type '{0}' contains no data.";
-public const string KnownTypeAttributeMethodNull = @"Method specified by KnownTypeAttribute attribute on type '{0}' returned null.";
-public const string MaxArrayLengthExceeded = @"The maximum array length ({0}) has been exceeded while reading XML data for array of type '{1}'.";
-public const string MissingGetSchemaMethod = @"Type '{0}' does not have a static method '{1}' that takes a parameter of type 'System.Xml.Schema.XmlSchemaSet' as specified by the XmlSchemaProviderAttribute attribute.";
-public const string MultipleIdDefinition = @"Invalid XML encountered. The same Id value '{0}' is defined more than once. Multiple objects cannot be deserialized using the same Id.";
-public const string NoConversionPossibleTo = @"An internal error has occurred. No conversion is possible to '{0}' - error generating code for serialization.";
-public const string NoGetMethodForProperty = @"No get method for property '{1}' in type '{0}'.";
-public const string NoSetMethodForProperty = @"No set method for property '{1}' in type '{0}'.";
-public const string NullKnownType = @"One of the known types provided to the serializer via '{0}' argument was invalid because it was null. All known types specified must be non-null values.";
-public const string NullValueReturnedForGetOnlyCollection = @"The get-only collection of type '{0}' returned a null value.  The input stream contains collection items which cannot be added if the instance is null.  Consider initializing the collection either in the constructor of the the object or in the getter.";
-public const string ObjectTableOverflow = @"An internal error has occurred. Object table overflow. This could be caused by serializing or deserializing extremely large object graphs.";
-public const string OrderCannotBeNegative = @"Property 'Order' in DataMemberAttribute attribute cannot be a negative number.";
-public const string ParameterCountMismatch = @"Invalid number of parameters to call method '{0}'. Expected '{1}' parameters, but '{2}' were provided.";
-public const string PartialTrustCollectionContractAddMethodNotPublic = @"The collection data contract type '{0}' cannot be deserialized because the method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustCollectionContractNoPublicConstructor = @"The collection data contract type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustCollectionContractTypeNotPublic = @"The collection data contract type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractOnSerializingNotPublic = @"The data contract type '{0}' cannot be serialized because the OnSerializing method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractOnSerializedNotPublic = @"The data contract type '{0}' cannot be serialized because the OnSerialized method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractOnDeserializingNotPublic = @"The data contract type '{0}' cannot be deserialized because the OnDeserializing method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractOnDeserializedNotPublic = @"The data contract type '{0}' cannot be deserialized because the OnDeserialized method '{1}' is not public. Making the method public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractFieldGetNotPublic = @"The data contract type '{0}' cannot be serialized because the member '{1}' is not public. Making the member public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractFieldSetNotPublic = @"The data contract type '{0}' cannot be deserialized because the member '{1}' is not public. Making the member public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractPropertyGetNotPublic = @"The data contract type '{0}' cannot be serialized because the property '{1}' does not have a public getter. Adding a public getter will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractPropertySetNotPublic = @"The data contract type '{0}' cannot be deserialized because the property '{1}' does not have a public setter. Adding a public setter will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustDataContractTypeNotPublic = @"The data contract type '{0}' is not serializable because it is not public. Making the type public will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustNonAttributedSerializableTypeNoPublicConstructor = @"The type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustIXmlSerializableTypeNotPublic = @"The IXmlSerializable type '{0}' is not serializable in partial trust because it is not public. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string PartialTrustIXmlSerialzableNoPublicConstructor = @"The IXmlSerializable type '{0}' cannot be deserialized because it does not have a public parameterless constructor. Adding a public parameterless constructor will fix this error. Alternatively, you can make it internal, and use the InternalsVisibleToAttribute attribute on your assembly in order to enable serialization of internal members - see documentation for more details. Be aware that doing so has certain security implications.";
-public const string NonAttributedSerializableTypesMustHaveDefaultConstructor = @"The Type '{0}' must have a parameterless constructor.";
-public const string AttributedTypesCannotInheritFromNonAttributedSerializableTypes = @"Type '{0}' cannot inherit from a type that is not marked with DataContractAttribute or SerializableAttribute.  Consider marking the base type '{1}' with DataContractAttribute or SerializableAttribute, or removing them from the derived type.";
-public const string GetOnlyCollectionsNotSupported = @"Get-only collection properties are not supported.  Consider adding a public setter to property '{0}.{1}' or marking the it with the IgnoreDataMemberAttribute. ";
-public const string QuotaMustBePositive = @"Quota must be a positive value.";
-public const string QuotaIsReadOnly = @"The '{0}' quota is readonly.";
-public const string QuotaCopyReadOnly = @"Cannot copy XmlDictionaryReaderQuotas. Target is readonly.";
-public const string RequiredMemberMustBeEmitted = @"Member {0} in type {1} cannot be serialized. This exception is usually caused by trying to use a null value where a null value is not allowed. The '{0}' member is set to its default value (usually null or zero). The member's EmitDefault setting is 'false', indicating that the member should not be serialized. However, the member's IsRequired setting is 'true', indicating that it must be serialized. This conflict cannot be resolved.  Consider setting '{0}' to a non-default value. Alternatively, you can change the EmitDefaultValue property on the DataMemberAttribute attribute to true, or changing the IsRequired property to false.";
-public const string ResolveTypeReturnedFalse = @"An object of type '{0}' which derives from DataContractResolver returned false from its TryResolveType method when attempting to resolve the name for an object of type '{1}', indicating that the resolution failed. Change the TryResolveType implementation to return true.";
-public const string ResolveTypeReturnedNull = @"An object of type '{0}' which derives from DataContractResolver returned a null typeName or typeNamespace but not both from its TryResolveType method when attempting to resolve the name for an object of type '{1}'. Change the TryResolveType implementation to return non-null values, or to return null values for both typeName and typeNamespace in order to serialize as the declared type.";
-public const string SupportForMultidimensionalArraysNotPresent = @"Multi-dimensional arrays are not supported.";
-public const string TooManyCollectionContracts = @"Type '{0}' has more than one CollectionDataContractAttribute attribute.";
-public const string TooManyDataContracts = @"Type '{0}' has more than one DataContractAttribute attribute.";
-public const string TooManyDataMembers = @"Member '{0}.{1}' has more than one DataMemberAttribute attribute.";
-public const string TooManyEnumMembers = @"Member '{0}.{1}' has more than one EnumMemberAttribute attribute.";
-public const string TooManyIgnoreDataMemberAttributes = @"Member '{0}.{1}' has more than one IgnoreDataMemberAttribute attribute.";
-public const string TypeMustBeConcrete = @"Error while getting known types for Type '{0}'. The type must not be an open or partial generic class.";
-public const string TypeNotSerializable = @"Type '{0}' cannot be serialized. Consider marking it with the DataContractAttribute attribute, and marking all of its members you want serialized with the DataMemberAttribute attribute. Alternatively, you can ensure that the type is public and has a parameterless constructor - all public members of the type will then be serialized, and no attributes will be required.";
-public const string UnexpectedContractType = @"An internal error has occurred. Unexpected contract type '{0}' for type '{1}' encountered.";
-public const string UnexpectedElementExpectingElements = @"'{0}' '{1}' from namespace '{2}' is not expected. Expecting element '{3}'.";
-public const string UnexpectedEndOfFile = @"Unexpected end of file.";
-public const string UnknownConstantType = @"Unrecognized constant type '{0}'.";
-public const string UnsupportedIDictionaryAsDataMemberType = @"Cannot deserialize one of the DataMember because it is an IDictionary. Use IDictionary<K,V> instead.";
-public const string ValueMustBeNonNegative = @"The value of this argument must be non-negative.";
-public const string ValueTypeCannotBeNull = @"ValueType '{0}' cannot be null.";
-public const string ValueTypeCannotHaveBaseType = @"Data contract '{0}' from namespace '{1}' is a value type and cannot have base contract '{2}' from namespace '{3}'.";
-public const string ValueTypeCannotHaveId = @"ValueType '{0}' cannot have id.";
-public const string ValueTypeCannotHaveIsReference = @"Value type '{0}' cannot have the IsReference setting of '{1}'. Either change the setting to '{2}', or remove it completely. ";
-public const string ValueTypeCannotHaveRef = @"ValueType '{0}' cannot have ref to another object.";
-public const string XmlElementAttributes = @"Only Element nodes have attributes.";
-public const string XmlForObjectCannotHaveContent = @"Element {0} from namespace {1} cannot have child contents to be deserialized as an object. Please use XElement to deserialize this pattern of XML.";
-public const string XmlInvalidConversion = @"The value '{0}' cannot be parsed as the type '{1}'.";
-public const string XmlInvalidConversionWithoutValue = @"The value cannot be parsed as the type '{0}'.";
-public const string XmlStartElementExpected = @"Start element expected. Found {0}.";
-public const string XmlWriterMustBeInElement = @"WriteState '{0}' not valid. Caller must write start element before serializing in contentOnly mode.";
-
-       }
-}
-
-namespace System.Runtime.Serialization
-{
-       static partial class SR {
-
-public const string OffsetExceedsBufferSize = @"The specified offset exceeds the buffer size ({0} bytes).";
-public const string SizeExceedsRemainingBufferSpace = @"The specified size exceeds the remaining buffer space ({0} bytes).";
-public const string ValueMustBeInRange = @"The value of this argument must fall within the range {0} to {1}.";
-public const string XmlArrayTooSmallOutput = @"Array too small.  Must be able to hold at least {0}.";
-public const string XmlInvalidBase64Length = @"Base64 sequence length ({0}) not valid. Must be a multiple of 4.";
-public const string XmlInvalidBase64Sequence = @"The characters '{0}' at offset {1} are not a valid Base64 sequence.";
-public const string XmlInvalidBinHexLength = @"BinHex sequence length ({0}) not valid. Must be a multiple of 2.";
-public const string XmlInvalidBinHexSequence = @"The characters '{0}' at offset {1} are not a valid BinHex sequence.";
-public const string XmlInvalidHighSurrogate = @"High surrogate char '0x{0}' not valid. High surrogate chars range from 0xD800 to 0xDBFF.";
-public const string XmlInvalidLowSurrogate = @"Low surrogate char '0x{0}' not valid. Low surrogate chars range from 0xDC00 to 0xDFFF.";
-public const string XmlInvalidSurrogate = @"Surrogate char '0x{0}' not valid. Surrogate chars range from 0x10000 to 0x10FFFF.";
-
-       }
-}
-
-namespace System.Runtime.Serialization
-{
-       static partial class SR {
-
-public const string CombinedPrefixNSLength = @"The combined length of the prefix and namespace must not be greater than {0}.";
-public const string InvalidInclusivePrefixListCollection = @"The inclusive namespace prefix collection cannot contain null as one of the items.";
-public const string InvalidLocalNameEmpty = @"The empty string is not a valid local name.";
-public const string XmlArrayTooSmall = @"Array too small.";
-public const string XmlArrayTooSmallInput = @"Array too small.  Length of available data must be at least {0}.";
-public const string XmlBadBOM = @"Unrecognized Byte Order Mark.";
-public const string XmlBase64DataExpected = @"Base64 encoded data expected. Found {0}.";
-public const string XmlCDATAInvalidAtTopLevel = @"CData elements not valid at top level of an XML document.";
-public const string XmlCloseCData = @"']]>' not valid in text node content.";
-public const string XmlConversionOverflow = @"The value '{0}' cannot be represented with the type '{1}'.";
-public const string XmlDeclarationRequired = @"An XML declaration with an encoding is required for all non-UTF8 documents.";
-public const string XmlDeclMissingVersion = @"Version not found in XML declaration.";
-public const string XmlDeclMissing = @"An XML declaration is required for all non-UTF8 documents.";
-public const string XmlDeclNotFirst = @"No characters can appear before the XML declaration.";
-public const string XmlDictionaryStringIDRange = @"XmlDictionaryString IDs must be in the range from {0} to {1}.";
-public const string XmlDictionaryStringIDUndefinedSession = @"XmlDictionaryString ID {0} not defined in the XmlBinaryReaderSession.";
-public const string XmlDictionaryStringIDUndefinedStatic = @"XmlDictionaryString ID {0} not defined in the static dictionary.";
-public const string XmlDuplicateAttribute = @"Duplicate attribute found. Both '{0}' and '{1}' are from the namespace '{2}'.";
-public const string XmlEmptyNamespaceRequiresNullPrefix = @"The empty namespace requires a null or empty prefix.";
-public const string XmlEncodingMismatch = @"The encoding in the declaration '{0}' does not match the encoding of the document '{1}'.";
-public const string XmlEncodingNotSupported = @"XML encoding not supported.";
-public const string XmlEndElementExpected = @"End element '{0}' from namespace '{1}' expected. Found {2}.";
-public const string XmlEndElementNoOpenNodes = @"No corresponding start element is open.";
-public const string XmlExpectedEncoding = @"The expected encoding '{0}' does not match the actual encoding '{1}'.";
-public const string XmlFoundCData = @"cdata '{0}'";
-public const string XmlFoundComment = @"comment '{0}'";
-public const string XmlFoundElement = @"element '{0}' from namespace '{1}'";
-public const string XmlFoundEndElement = @"end element '{0}' from namespace '{1}'";
-public const string XmlFoundEndOfFile = @"end of file";
-public const string XmlFoundNodeType = @"node {0}";
-public const string XmlFoundText = @"text '{0}'";
-public const string XmlFullStartElementExpected = @"Non-empty start element expected. Found {0}.";
-public const string XmlFullStartElementLocalNameNsExpected = @"Non-empty start element '{0}' from namespace '{1}' expected. Found {2}.";
-public const string XmlFullStartElementNameExpected = @"Non-empty start element '{0}' expected. Found {1}.";
-public const string XmlIDDefined = @"ID already defined.";
-public const string XmlKeyAlreadyExists = @"The specified key already exists in the dictionary.";
-public const string XmlIllegalOutsideRoot = @"Text cannot be written outside the root element.";
-public const string XmlInvalidBytes = @"Invalid byte encoding.";
-public const string XmlInvalidCharRef = @"Character reference not valid.";
-public const string XmlInvalidCommentChars = @"XML comments cannot contain '--' or end with '-'.";
-public const string XmlInvalidDeclaration = @"XML declaration can only be written at the beginning of the document.";
-public const string XmlInvalidDepth = @"Cannot call '{0}' while Depth is '{1}'.";
-public const string XmlInvalidEncoding = @"XML encoding must be 'UTF-8'.";
-public const string XmlInvalidFFFE = @"Characters with hexadecimal values 0xFFFE and 0xFFFF are not valid.";
-public const string XmlInvalidFormat = @"The input source is not correctly formatted.";
-public const string XmlInvalidID = @"ID must be >= 0.";
-public const string XmlInvalidOperation = @"The reader cannot be advanced.";
-public const string XmlInvalidPrefixState = @"A prefix cannot be defined while WriteState is '{0}'.";
-public const string XmlInvalidQualifiedName = @"Expected XML qualified name. Found '{0}'.";
-public const string XmlInvalidRootData = @"The data at the root level is invalid.";
-public const string XmlInvalidStandalone = @"'standalone' value in declaration must be 'yes' or 'no'.";
-public const string XmlInvalidStream = @"Stream returned by IStreamProvider cannot be null.";
-public const string XmlInvalidUniqueId = @"UniqueId cannot be zero length.";
-public const string XmlInvalidUTF8Bytes = @"'{0}' contains invalid UTF8 bytes.";
-public const string XmlInvalidVersion = @"XML version must be '1.0'.";
-public const string XmlInvalidWriteState = @"'{0}' cannot be called while WriteState is '{1}'.";
-public const string XmlInvalidXmlByte = @"The byte 0x{0} is not valid at this location.";
-public const string XmlInvalidXmlSpace = @"'{0}' is not a valid xml:space value. Valid values are 'default' and 'preserve'.";
-public const string XmlLineInfo = @"Line {0}, position {1}.";
-public const string XmlMalformedDecl = @"Malformed XML declaration.";
-public const string XmlMaxArrayLengthExceeded = @"The maximum array length quota ({0}) has been exceeded while reading XML data. This quota may be increased by changing the MaxArrayLength property on the XmlDictionaryReaderQuotas object used when creating the XML reader.";
-
-
-public const string XmlMaxNameTableCharCountExceeded = @"The maximum nametable character count quota ({0}) has been exceeded while reading XML data. The nametable is a data structure used to store strings encountered during XML processing - long XML documents with non-repeating element names, attribute names and attribute values may trigger this quota. This quota may be increased by changing the MaxNameTableCharCount property on the XmlDictionaryReaderQuotas object used when creating the XML reader.";
-
-public const string XmlMethodNotSupported = @"This XmlWriter implementation does not support the '{0}' method.";
-public const string XmlMissingLowSurrogate = @"The surrogate pair is invalid. Missing a low surrogate character.";
-public const string XmlMultipleRootElements = @"There are multiple root elements.";
-public const string XmlNamespaceNotFound = @"The namespace '{0}' is not defined.";
-public const string XmlNestedArraysNotSupported = @"Nested arrays are not supported.";
-public const string XmlNoRootElement = @"The document does not have a root element.";
-public const string XmlOnlyOneRoot = @"Only one root element is permitted per document.";
-public const string XmlOnlyWhitespace = @"Only white space characters can be written with this method.";
-public const string XmlOnlySingleValue = @"Only a single typed value may be written inside an attribute or content.";
-public const string XmlPrefixBoundToNamespace = @"The prefix '{0}' is bound to the namespace '{1}' and cannot be changed to '{2}'.";
-public const string XmlProcessingInstructionNotSupported = @"Processing instructions (other than the XML declaration) and DTDs are not supported.";
-public const string XmlReservedPrefix = @"Prefixes beginning with ""xml"" (regardless of casing) are reserved for use by XML.";
-public const string XmlSpaceBetweenAttributes = @"Whitespace must appear between attributes.";
-public const string XmlSpecificBindingNamespace = @"The namespace '{1}' can only be bound to the prefix '{0}'.";
-public const string XmlSpecificBindingPrefix = @"The prefix '{0}' can only be bound to the namespace '{1}'.";
-public const string XmlStartElementLocalNameNsExpected = @"Start element '{0}' from namespace '{1}' expected. Found {2}.";
-public const string XmlStartElementNameExpected = @"Start element '{0}' expected. Found {1}.";
-public const string XmlTagMismatch = @"Start element '{0}' does not match end element '{1}'.";
-public const string XmlTokenExpected = @"The token '{0}' was expected but found '{1}'.";
-public const string XmlUndefinedPrefix = @"The prefix '{0}' is not defined.";
-public const string XmlUnexpectedEndElement = @"No matching start tag for end element.";
-public const string XmlUnexpectedEndOfFile = @"Unexpected end of file. Following elements are not closed: {0}.";
-public const string XmlWriterClosed = @"The XmlWriter is closed.";
-public const string Xml_InvalidNmToken = @"Invalid NmToken value '{0}'.";
-
-       }
-}
-
-#endregion
+}
\ No newline at end of file
diff --git a/mcs/class/System.Runtime.Serialization/ReferenceSources/SR.missing.cs b/mcs/class/System.Runtime.Serialization/ReferenceSources/SR.missing.cs
new file mode 100644 (file)
index 0000000..aa1b841
--- /dev/null
@@ -0,0 +1,312 @@
+using System.Globalization;
+
+namespace System.Runtime.Serialization
+{
+       static partial class SR
+       {
+               internal static string GetString(string name, params object[] args)
+               {
+                       return GetString (CultureInfo.InvariantCulture, name, args);
+               }
+
+               internal static string GetString(CultureInfo culture, string name, params object[] args)
+               {
+                       return string.Format (culture, name, args);
+               }
+
+               internal static string GetString(string name)
+               {
+                       return name;
+               }
+
+               internal static string GetString(CultureInfo culture, string name)
+               {
+                       return name;
+               }
+
+#region MissingInStrings.txt
+
+//
+// This was retrieved as follows:
+//
+// 1. mcs ReferenceSources/SR.cs -t:library -out:existing.dll
+// 2. mcs {https://raw.githubusercontent.com/mono/mono/wip-serialization-halfway/mcs/class/System.Runtime.Serialization/ReferenceSource/SR.cs} -t:library -out:full.dll
+// 3. csharp -e "System.IO.File.WriteAllLines ("existing.txt", System.Reflection.Assembly.ReflectionOnlyLoadFrom ("existing.dll").GetTypes ().SelectMany (t => t.GetFields ()).Select (f => f.Name).ToArray ())"
+// 4. csharp -e "System.IO.File.WriteAllLines ("full.txt", System.Reflection.Assembly.ReflectionOnlyLoadFrom ("full.dll").GetTypes ().SelectMany (t => t.GetFields ()).Select (f => f.Name).ToArray ())"
+// 5. csharp
+//     var existing = System.IO.File.ReadAllLines ("existing.txt");
+//     var full = System.IO.File.ReadAllLines ("full.txt");
+//  var missing = full.Where (f => !existing.Contains (f));
+//  System.IO.File.WriteAllLines ("missing.cs", missing.Select (m => "public const string " + m + " = @\"" + m + "\";").ToArray ())
+// 6. copy missing.cs contents here.
+//
+
+public const string AbstractElementNotSupported = @"Abstract element '{0}' is not supported.";
+public const string AbstractTypeNotSupported = @"Abstract type is not supported";
+public const string AmbiguousReferencedCollectionTypes1 = @"Ambiguous collection types were referenced: {0}";
+public const string AmbiguousReferencedCollectionTypes3 = @"In '{0}' element in '{1}' namespace, ambiguous collection types were referenced: {2}";
+public const string AmbiguousReferencedTypes1 = @"Ambiguous types were referenced: {0}";
+public const string AmbiguousReferencedTypes3 = @"In '{0}' element in '{1}' namespace, ambiguous types were referenced: {2}";
+public const string AnnotationAttributeNotFound = @"Annotation attribute was not found: default value annotation is '{0}', type is '{1}' in '{2}' namespace, emit default value is {3}.";
+public const string AnonymousTypeNotSupported = @"Anonymous type is not supported. Type is '{0}' in '{1}' namespace.";
+public const string AnyAttributeNotSupported = @"XML Schema 'any' attribute is not supported";
+public const string ArrayItemFormMustBe = @"For array item, element 'form' must be {0}.";
+public const string ArraySizeAttributeIncorrect = @"Array size attribute is incorrect; must be between {0} and {1}.";
+
+public const string ArrayTypeCannotBeImported = @"Array type cannot be imported for '{0}' in '{1}' namespace: {2}.";
+public const string AssemblyNotFound = @"Assembly '{0}' was not found.";
+public const string AttributeNotFound = @"Attribute was not found for CLR type '{1}' in namespace '{0}'. XML reader node is on {2}, '{4}' node in '{3}' namespace.";
+public const string BaseTypeNotISerializable = @"Base type '{0}' in '{1}' namespace is not ISerializable.";
+public const string CannotComputeUniqueName = @"Cannot compute unique name for '{0}'.";
+public const string CannotDeriveFromSealedReferenceType = @"Cannod drive from sealed reference type '{2}', for '{0}' element in '{1}' namespace.";
+public const string CannotDeserializeForwardedType = @"Cannot deserialize forwarded type '{0}'.";
+public const string CannotExportNullAssembly = @"Cannot export null assembly.";
+public const string CannotExportNullKnownType = @"Cannot export null known type.";
+public const string CannotExportNullType = @"Cannot export null type.";
+public const string CannotHaveDuplicateAttributeNames = @"Cannot have duplicate attribute names '{0}'.";
+public const string CannotHaveDuplicateElementNames = @"Cannot have duplicate element names '{0}'.";
+public const string CannotImportInvalidSchemas = @"Cannot import invalid schemas.";
+public const string CannotImportNullDataContractName = @"Cannot import data contract with null name.";
+public const string CannotImportNullSchema = @"Cannot import from schema list that contains null.";
+public const string CannotSetMembersForReferencedType = @"Cannot set members for already referenced type. Base type is '{0}'.";
+public const string CannotSetNamespaceForReferencedType = @"Cannot set namespace for already referenced type. Base type is '{0}'.";
+public const string CannotUseGenericTypeAsBase = @"For '{0}' in '{1}' namespace, generic type cannot be referenced as the base type.";
+public const string ChangingFullTypeNameNotSupported = @"Changing full type name is not supported. Serialization type name: '{0}', data contract type name: '{1}'.";
+public const string CircularTypeReference = @"Circular type reference was found for '{0}' in '{1}' namespace.";
+public const string ClassDataContractReturnedForGetOnlyCollection = @"For '{0}' type, class data contract was returned for get-only collection.";
+public const string CLRNamespaceMappedMultipleTimes = @"CLR namespace is mapped multiple times. Current data contract namespace is '{0}', found '{1}' for CLR namespace '{2}'.";
+public const string ClrTypeNotFound = @"CLR type '{1}' in assembly '{0}' is not found.";
+public const string CollectionAssignedToIncompatibleInterface = @"Collection of type '{0}' is assigned to an incompatible interface '{1}'";
+public const string ComplexTypeRestrictionNotSupported = @"XML schema complexType restriction is not supported.";
+public const string ConfigDataContractSerializerSectionLoadError = @"Failed to load configuration section for dataContractSerializer.";
+public const string ConfigIndexOutOfRange = @"For type '{0}', configuration index is out of range.";
+public const string ConfigMustOnlyAddParamsWithType = @"Configuration parameter element must only add params with type."; // huh? the code doesn't make a lot of sense to me...
+public const string ConfigMustOnlySetTypeOrIndex = @"Configuration parameter element can set only one of either type or index.";
+public const string ConfigMustSetTypeOrIndex = @"Configuration parameter element must set either type or index.";
+public const string CouldNotReadSerializationSchema = @"Could not read serialization schema for '{0}' namespace.";
+public const string DefaultOnElementNotSupported = @"On element '{0}', default value is not supported.";
+public const string DerivedTypeNotISerializable = @"On type '{0}' in '{1}' namespace, derived type is not ISerializable.";
+public const string DupContractInDataContractSet = @"Duplicate contract in data contract set was found, for '{0}' in '{1}' namespace.";
+public const string DuplicateExtensionDataSetMethod = @"Duplicate extension data set method was found, for method '{0}', existing method is '{1}', on data contract type '{2}'.";
+public const string DupTypeContractInDataContractSet = @"Duplicate type contract in data contract set. Type name '{0}', for data contract '{1}' in '{2}' namespace.";
+public const string ElementMaxOccursMustBe = @"On element '{0}', schema element maxOccurs must be 1.";
+public const string ElementMinOccursMustBe = @"On element '{0}', schema element minOccurs must be less or equal to 1.";
+public const string ElementRefOnLocalElementNotSupported = @"For local element, ref is not supported. The referenced name is '{0}' in '{1}' namespace.";
+public const string EnumEnumerationFacetsMustHaveValue = @"Schema enumeration facet must have values.";
+public const string EnumListInAnonymousTypeNotSupported = @"Enum list in anonymous type is not supported.";
+public const string EnumListMustContainAnonymousType = @"Enum list must contain an anonymous type.";
+public const string EnumOnlyEnumerationFacetsSupported = @"For schema facets, only enumeration is supported.";
+public const string EnumRestrictionInvalid = @"For simpleType restriction, only enum is supported and this type could not be convert to enum.";
+public const string EnumTypeCannotBeImported = @"For '{0}' in '{1}' namespace, enum type cannot be imported: {2}";
+public const string EnumTypeNotSupportedByDataContractJsonSerializer = @"Enum type is not supported by DataContractJsonSerializer. The underlying type is '{0}'.";
+public const string EnumUnionInAnonymousTypeNotSupported = @"Enum union in anonymous type is not supported.";
+public const string ExtensionDataSetMustReturnVoid = @"For type '{0}' method '{1}', extension data set method must return void.";
+public const string ExtensionDataSetParameterInvalid = @"For type '{0}' method '{1}', extension data set method has invalid type of parameter '{2}'.";
+public const string FactoryObjectContainsSelfReference = @"Factory object contains a reference to self. Old object is '{0}', new object is '{1}'.";
+public const string FactoryTypeNotISerializable = @"For data contract '{1}', factory type '{0}' is not ISerializable.";
+public const string FixedOnElementNotSupported = @"On schema element '{0}', fixed value is not supported.";
+public const string FlushBufferAlreadyInUse = @"Flush buffer is already in use.";
+public const string FormMustBeQualified = @"On schema element '{0}', form must be qualified.";
+public const string GenericAnnotationAttributeNotFound = @"On type '{0}' Generic annotation attribute '{1}' was not found.";
+public const string GenericAnnotationForNestedLevelMustBeIncreasing = @"On type '{2}', generic annotation for nested level must be increasing. Argument element is '{0}' in '{1}' namespace.";
+public const string GenericAnnotationHasInvalidAttributeValue = @"On type '{2}', generic annotation has invalid attribute value '{3}'. Argument element is '{0}' in '{1}' namespace. Nested level attribute attribute name is '{4}'. Type is '{5}'."; // dunno if this makes sense...
+public const string GenericAnnotationHasInvalidElement = @"On type '{2}', generic annotation has invalid element. Argument element is '{0}' in '{1}' namespace.";
+public const string GenericTypeNameMismatch = @"Generic type name mismatch. Expected '{0}' in '{1}' namespace, got '{2}' in '{3}' namespace instead.";
+public const string GenericTypeNotExportable = @"Generic type '{0}' is not exportable.";
+public const string GetOnlyCollectionMustHaveAddMethod = @"On type '{0}', get-only collection must have an Add method.";
+public const string GetRealObjectReturnedNull = @"On the surrogate data contract for '{0}', GetRealObject method returned null.";
+public const string InvalidAnnotationExpectingText = @"For annotation element '{0}' in namespace '{1}', expected text but got element '{2}' in '{3}' namespace.";
+public const string InvalidAssemblyFormat = @"'{0}': invalid assembly format.";
+public const string InvalidCharacterEncountered = @"Encountered an invalid character '{0}'.";
+public const string InvalidClassDerivation = @"Invalid class derivation from '{0}' in '{1}' namespace.";
+public const string InvalidClrNameGeneratedForISerializable = @"Invalid CLR name '{2}' is generated for ISerializable type '{0}' in '{1}' namespace.";
+public const string InvalidClrNamespaceGeneratedForISerializable = @"Invalid CLR namespace '{3}' is generated for ISerializable type '{0}' in '{1}' namespace. Data contract namespace from the URI would be generated as '{2}'.";
+public const string InvalidDataNode = @"Invalid data node for '{0}' type.";
+public const string InvalidEmitDefaultAnnotation = @"Invalid EmilDefault annotation for '{0}' in type '{1}' in '{2}' namespace.";
+public const string InvalidEnumBaseType = @"Invalid enum base type is specified for type '{0}' in '{1}' namespace, element name is '{2}' in '{3}' namespace.";
+public const string InvalidISerializableDerivation = @"Invalid ISerializable derivation from '{0}' in '{1}' namespace.";
+public const string InvalidKeyValueType = @"'{0}' is an invalid key value type.";
+public const string InvalidKeyValueTypeNamespace = @"'{0}' in '{1}' namespace is an invalid key value type.";
+public const string InvalidReturnSchemaOnGetSchemaMethod = @"On type '{0}', the return value from GetSchema method was invalid.";
+public const string InvalidStateInExtensionDataReader = @"Invalid state in extension data reader.";
+public const string InvalidXmlDeserializingExtensionData = @"Invalid XML while deserializing extension data.";
+public const string IsAnyNotSupportedByNetDataContractSerializer = @"For type '{0}', IsAny is not supported by NetDataContractSerializer.";
+public const string IsDictionaryFormattedIncorrectly = @"IsDictionary formatted value '{0}' is incorrect: {1}";
+public const string ISerializableAssemblyNameSetToZero = @"ISerializable AssemblyName is set to ""0"" for type '{0}'.";
+public const string ISerializableCannotHaveDataContract = @"ISerializable type '{0}' cannot have DataContract.";
+public const string ISerializableContainsMoreThanOneItems = @"ISerializable cannot contain more than one item.";
+public const string ISerializableDerivedContainsOneOrMoreItems = @"Type derived from ISerializable cannot contain more than one item.";
+public const string ISerializableDoesNotContainAny = @"ISerializable does not contain any element.";
+public const string ISerializableMustRefFactoryTypeAttribute = @"ISerializable must have ref attribute that points to its factory type.";
+public const string ISerializableTypeCannotBeImported = @"ISerializable type '{0}' in '{1}' namespace cannot be imported: {2}";
+public const string ISerializableWildcardMaxOccursMustBe = @"ISerializable wildcard maxOccurs must be '{0}'.";
+public const string ISerializableWildcardMinOccursMustBe = @"ISerializable wildcard maxOccurs must be '{0}'.";
+public const string ISerializableWildcardNamespaceInvalid = @"ISerializable wildcard namespace is invalid: '{0}'.";
+public const string ISerializableWildcardProcessContentsInvalid = @"ISerializable wildcard processContents is invalid: '{0}'.";
+public const string IsReferenceGetOnlyCollectionsNotSupported = @"On type '{1}', attribute '{0}' points to get-only collection, which is not supported.";
+public const string IsValueTypeFormattedIncorrectly = @"IsValueType is formatted incorrectly as '{0}': {1}";
+public const string JsonAttributeAlreadyWritten = @"JSON attribute '{0}' is already written.";
+public const string JsonAttributeMustHaveElement = @"JSON attribute must have an owner element.";
+public const string JsonCannotWriteStandaloneTextAfterQuotedText = @"JSON writer cannot write standalone text after quoted text.";
+public const string JsonCannotWriteTextAfterNonTextAttribute = @"JSON writer cannot write text after non-text attribute. Data type is '{0}'.";
+public const string JsonDateTimeOutOfRange = @"JSON DateTime is out of range.";
+public const string JsonDuplicateMemberInInput = @"Duplicate member '{0}' is found in JSON input.";
+public const string JsonDuplicateMemberNames = @"Duplicate member, including '{1}', is found in JSON input, in type '{0}'.";
+public const string JsonEncodingNotSupported = @"JSON Encoding is not supported.";
+public const string JsonEncounteredUnexpectedCharacter = @"Encountered an unexpected character '{0}' in JSON.";
+public const string JsonEndElementNoOpenNodes = @"Encountered an end element while there was no open element in JSON writer.";
+public const string JsonExpectedEncoding = @"Expected encoding '{0}', got '{1}' instead.";
+public const string JsonInvalidBytes = @"Invalid bytes in JSON.";
+public const string JsonInvalidDataTypeSpecifiedForServerType = @"The specified data type is invalid for server type. Type: '{0}', specified data type: '{1}', server type: '{2}', object '{3}'."; // I wonder if this makes sense...
+public const string JsonInvalidDateTimeString = @"Invalid JSON dateTime string is specified: original value '{0}', start guide writer: {1}, end guard writer: {2}.";
+public const string JsonInvalidFFFE = @"FFFE in JSON is invalid.";
+public const string JsonInvalidItemNameForArrayElement = @"Invalid JSON item name '{0}' for array element (item element is '{1}' in JSON).";
+public const string JsonInvalidLocalNameEmpty = @"Empty string is invalid as a local name.";
+public const string JsonInvalidMethodBetweenStartEndAttribute = @"Invalid method call state between start and end attribute.";
+public const string JsonInvalidRootElementName = @"Invalid root element name '{0}' (root element is '{1}' in JSON).";
+public const string JsonInvalidStartElementCall = @"Invalid call to JSON WriteStartElement method.";
+public const string JsonInvalidWriteState = @"Invalid write state {1} for '{0}' method.";
+public const string JsonMethodNotSupported = @"Method {0} is not supported in JSON.";
+public const string JsonMultipleRootElementsNotAllowedOnWriter = @"Multiple root element is not allowed on JSON writer.";
+public const string JsonMustSpecifyDataType = @"On JSON writer data type '{0}' must be specified. Object string is '{1}', server type string is '{2}'.";
+public const string JsonMustUseWriteStringForWritingAttributeValues = @"On JSON writer WriteString must be used for writing attribute values.";
+public const string JsonNamespaceMustBeEmpty = @"JSON namespace is specified as '{0}' but it must be empty.";
+public const string JsonNestedArraysNotSupported = @"Nested array is not supported in JSON: '{0}'";
+public const string JsonNodeTypeArrayOrObjectNotSpecified = @"Either Object or Array of JSON node type must be specified.";
+public const string JsonNoMatchingStartAttribute = @"WriteEndAttribute was called while there is no open attribute.";
+public const string JsonOffsetExceedsBufferSize = @"On JSON writer, offset exceeded buffer size {0}.";
+public const string JsonOneRequiredMemberNotFound = @"Required member {1} in type '{0}' is not found.";
+public const string JsonOnlyWhitespace = @"Only whitespace characters are allowed for {1} method. The specified value is '{0}'";
+public const string JsonOpenAttributeMustBeClosedFirst = @"JSON attribute must be closed first before calling {0} method.";
+public const string JsonPrefixMustBeNullOrEmpty = @"JSON prefix must be null or empty. '{0}' is specified instead.";
+public const string JsonRequiredMembersNotFound = @"Required members {0} in type '{1}' are not found.";
+public const string JsonServerTypeSpecifiedForInvalidDataType = @"Server type is specified for invalid data type in JSON. Server type: '{0}', type: '{1}', dataType: '{2}', object: '{3}'.";
+public const string JsonSizeExceedsRemainingBufferSpace = @"JSON size exceeded remaining buffer space, by {0} byte(s).";
+public const string JsonTypeNotSupportedByDataContractJsonSerializer = @"Type '{0}' is not suppotred by DataContractJsonSerializer.";
+public const string JsonUnexpectedAttributeLocalName = @"Unexpected attribute local name '{0}'.";
+public const string JsonUnexpectedAttributeValue = @"Unexpected attribute value '{0}'.";
+public const string JsonUnexpectedEndOfFile = @"Unexpected end of file in JSON.";
+public const string JsonUnsupportedForIsReference = @"Unsupported value for IsReference for type '{0}', IsReference value is {1}.";
+public const string JsonWriteArrayNotSupported = @"JSON WriteArray is not supported.";
+public const string JsonWriterClosed = @"JSON writer is already closed.";
+public const string JsonXmlInvalidDeclaration = @"Attempt to write invalid XML declration.";
+public const string JsonXmlProcessingInstructionNotSupported = @"processing instruction is not supported in JSON writer.";
+public const string KeyTypeCannotBeParsedInSimpleDictionary = @"Key type '{1}' for collection type '{0}' cannot be parsed in simple dictionary.";
+public const string KnownTypeConfigGenericParamMismatch = @"Generic parameter count do not match between known type and configuration. Type is '{0}', known type has {1} parameters, configuration has {2} parameters.";
+public const string KnownTypeConfigIndexOutOfBounds = @"For known type configuration, index is out of bound. Root type: '{0}' has {1} type arguments, and index was {2}.";
+public const string KnownTypeConfigIndexOutOfBoundsZero = @"For known type configuration, index is out of bound. Root type: '{0}' has {1} type arguments, and index was {2}.";
+public const string KnownTypeConfigObject = @"Known type configuration specifies System.Object.";
+public const string MaxMimePartsExceeded = @"MIME parts number exceeded the maximum settings. Must be less than {0}. Specified as '{1}'.";
+public const string MimeContentTypeHeaderInvalid = @"MIME content type header is invalid.";
+public const string MimeHeaderInvalidCharacter = @"MIME header has an invalid character ('{0}', {1} in hexadecimal value).";
+public const string MimeMessageGetContentStreamCalledAlready = @"On MimeMessage, GetContentStream method is already called.";
+public const string MimeReaderHeaderAlreadyExists = @"MIME header '{0}' already exists.";
+public const string MimeReaderMalformedHeader = @"Malformed MIME header.";
+public const string MimeReaderResetCalledBeforeEOF = @"On MimeReader, Reset method is called before EOF.";
+public const string MimeReaderTruncated = @"MIME parts are truncated.";
+public const string MimeVersionHeaderInvalid = @"MIME version header is invalid.";
+public const string MimeWriterInvalidStateForClose = @"MIME writer is at invalid state for closing.";
+public const string MimeWriterInvalidStateForContent = @"MIME writer is at invalid state for content.";
+public const string MimeWriterInvalidStateForHeader = @"MIME writer is at invalid state for header.";
+public const string MimeWriterInvalidStateForStartPart = @"MIME writer is at invalid state for starting a part.";
+public const string MimeWriterInvalidStateForStartPreface = @"MIME writer is at invalid state for starting preface.";
+public const string MissingSchemaType = @"Schema type '{0}' is missing and required for '{1}' type.";
+public const string MixedContentNotSupported = @"Mixed content is not supported.";
+public const string MtomBoundaryInvalid = @"MIME boundary is invalid: '{0}'.";
+public const string MtomBufferQuotaExceeded = @"MTOM buffer quota exceeded. The maximum size is {0}.";
+public const string MtomContentTransferEncodingNotPresent = @"MTOM content transfer encoding is not present. ContentTransferEncoding header is '{0}'.";
+public const string MtomContentTransferEncodingNotSupported = @"MTOM content transfer encoding value is not supported. Raw value is '{0}', '{1}' in 7bit encoding, '{2}' in 8bit encoding, and '{3}' in binary.";
+public const string MtomContentTypeInvalid = @"MTOM content type is invalid.";
+public const string MtomDataMustNotContainXopInclude = @"MTOM data must not contain xop:Include element. '{0}' element in '{1}' namespace.";
+public const string MtomExceededMaxSizeInBytes = @"MTOM exceeded max size in bytes. The maximum size is {0}.";
+public const string MtomInvalidCIDUri = @"Invalid MTOM CID URI: '{0}'.";
+public const string MtomInvalidEmptyURI = @"empty URI is invalid for MTOM MIME part.";
+public const string MtomInvalidStartUri = @"Invalid MTOM start URI: '{0}'.";
+public const string MtomInvalidTransferEncodingForMimePart = @"Invalid transfer encoding for MIME part: '{0}', in binary: '{1}'.";
+public const string MtomMessageContentTypeNotFound = @"MTOM message content type was not found.";
+public const string MtomMessageInvalidContent = @"MTOM message content is invalid.";
+public const string MtomMessageInvalidContentInMimePart = @"MTOM message content in MIME part is invalid.";
+public const string MtomMessageInvalidMimeVersion = @"MTOM message has invalid MIME version. Expected '{1}', got '{0}' instead.";
+public const string MtomMessageNotApplicationXopXml = @"MTOM msssage type is not '{0}'.";
+public const string MtomMessageNotMultipart = @"MTOM message is not multipart: media type should be '{0}', media subtype should be '{1}'.";
+public const string MtomMessageRequiredParamNotSpecified = @"Required MTOM parameter '{0}' is not specified.";
+public const string MtomMimePartReferencedMoreThanOnce = @"Specified MIME part '{0}' is referenced more than once.";
+public const string MtomPartNotFound = @"MTOM part with URI '{0}' is not found.";
+public const string MtomRootContentTypeNotFound = @"MTOM root content type is not found.";
+public const string MtomRootNotApplicationXopXml = @"MTOM root should have media type '{0}' and subtype '{1}'.";
+public const string MtomRootPartNotFound = @"MTOM root part is not found.";
+public const string MtomRootRequiredParamNotSpecified = @"Required MTOM root parameter '{0}' is not specified.";
+public const string MtomRootUnexpectedCharset = @"Unexpected charset on MTOM root. Expected '{1}', got '{0}' instead.";
+public const string MtomRootUnexpectedType = @"Unexpected type on MTOM root. Expected '{1}', got '{0}' instead.";
+public const string MtomXopIncludeHrefNotSpecified = @"xop Include element did not specify '{0}' attribute.";
+public const string MtomXopIncludeInvalidXopAttributes = @"xop Include element has invalid attribute: '{0}' in '{1}' namespace.";
+public const string MtomXopIncludeInvalidXopElement = @"xop Include element has invalid element: '{0}' in '{1}' namespace.";
+public const string MustContainOnlyLocalElements = @"Only local elements can be imported.";
+public const string NoAsyncWritePending = @"No async write operation is pending.";
+public const string NonOptionalFieldMemberOnIsReferenceSerializableType = @"For type '{0}', non-optional field member '{1}' is on the Serializable type that has IsReference as {2}.";
+public const string OnlyDataContractTypesCanHaveExtensionData = @"On '{0}' type, only DataContract types can have extension data.";
+public const string PartialTrustISerializableNoPublicConstructor = @"Partial trust access required for the constructor on the ISerializable type '{0}'";
+public const string QueryGeneratorPathToMemberNotFound = @"The path to member was not found for XPath query generator.";
+public const string ReadNotSupportedOnStream = @"Read operation is not supported on the Stream.";
+public const string ReadOnlyClassDeserialization = @"Error on deserializing read-only members in the class: {0}";
+public const string ReadOnlyCollectionDeserialization = @"Error on deserializing read-only collection: {0}";
+public const string RecursiveCollectionType = @"Type '{0}' involves recursive collection.";
+public const string RedefineNotSupported = @"XML Schema 'redefine' is not supported.";
+public const string ReferencedBaseTypeDoesNotExist = @"Referenced base type does not exist. Data contract name: '{0}' in '{1}' namespace, expected type: '{2}' in '{3}' namespace. Collection can be '{4}' or '{5}'."; // is it the expected message? I'm quite unsure.
+public const string ReferencedCollectionTypesCannotContainNull = @"Referenced collection types cannot contain null.";
+public const string ReferencedTypeDoesNotMatch = @"Referenced type '{0}' does not match the expected type '{1}' in '{2}' namespace.";
+public const string ReferencedTypeMatchingMessage = @"Reference type matches.";
+public const string ReferencedTypeNotMatchingMessage = @"Reference type does not match.";
+public const string ReferencedTypesCannotContainNull = @"Referenced types cannot contain null.";
+public const string RequiresClassDataContractToSetIsISerializable = @"To set IsISerializable, class data cotnract is required.";
+public const string RootParticleMustBeSequence = @"Root particle must be sequence to be imported.";
+public const string RootSequenceMaxOccursMustBe = @"On root sequence, maxOccurs must be 1.";
+public const string RootSequenceMustBeRequired = @"Root sequence must have an item and minOccurs must be 1.";
+public const string SeekNotSupportedOnStream = @"Seek operation is not supported on this Stream.";
+public const string SerializationInfo_ConstructorNotFound = @"Constructor that takes SerializationInfo and StreamingContext is not found for '{0}'.";
+public const string SimpleContentNotSupported = @"Simple content is not supported.";
+public const string SimpleTypeRestrictionDoesNotSpecifyBase = @"This simpleType restriction does not specify the base type.";
+public const string SimpleTypeUnionNotSupported = @"simpleType union is not supported.";
+public const string SpecifiedTypeNotFoundInSchema = @"Specified type '{0}' in '{1}' namespace is not found in the schemas.";
+public const string SubstitutionGroupOnElementNotSupported = @"substitutionGroups on elements are not supported.";
+public const string SurrogatesWithGetOnlyCollectionsNotSupported = @"Surrogates with get-only collections are not supported. Type '{1}' contains '{2}' which is of '{0}' type.";
+public const string SurrogatesWithGetOnlyCollectionsNotSupportedSerDeser = @"Surrogates with get-only collections are not supported. Found on type '{0}'.";
+public const string TopLevelElementRepresentsDifferentType = @"Top-level element represents a different type. Expected '{0}' type in '{1}' namespace.";
+public const string TraceCodeElementIgnored = @"Element ignored";
+public const string TraceCodeFactoryTypeNotFound = @"Factory type not found";
+public const string TraceCodeObjectWithLargeDepth = @"Object with large depth";
+public const string TraceCodeReadObjectBegin = @"ReadObject begins";
+public const string TraceCodeReadObjectEnd = @"ReadObject ends";
+public const string TraceCodeWriteObjectBegin = @"WriteObject begins";
+public const string TraceCodeWriteObjectContentBegin = @"WriteObjectContent begins";
+public const string TraceCodeWriteObjectContentEnd = @"WriteObjectContent ends";
+public const string TraceCodeWriteObjectEnd = @"WriteObject ends";
+public const string TraceCodeXsdExportAnnotationFailed = @"XSD export annotation failed";
+public const string TraceCodeXsdExportBegin = @"XSD export begins";
+public const string TraceCodeXsdExportDupItems = @"XSD export duplicate items";
+public const string TraceCodeXsdExportEnd = @"XSD export ends";
+public const string TraceCodeXsdExportError = @"XSD export error";
+public const string TraceCodeXsdImportAnnotationFailed = @"XSD import annotation failed";
+public const string TraceCodeXsdImportBegin = @"XSD import begins";
+public const string TraceCodeXsdImportEnd = @"XSD import ends";
+public const string TraceCodeXsdImportError = @"XSD import error";
+public const string TypeCannotBeForwardedFrom = @"Type '{0}' in assembly '{1}' cannot be forwarded from assembly '{2}'.";
+public const string TypeCannotBeImported = @"Type '{0}' in '{1}' namespace cannot be imported: {2}";
+public const string TypeCannotBeImportedHowToFix = @"Type cannot be imported: {0}"; // I cannot see where HowToFix is given from...
+public const string TypeHasNotBeenImported = @"Type '{0}' in '{1}' namespace has not been imported.";
+public const string TypeMustBeIXmlSerializable = @"Type '{0}' must be IXmlSerializable. Contract type: '{1}', contract name: '{2}' in '{3}' namespace.";
+public const string TypeShouldNotContainAttributes = @"Type should not contain attributes. Serialization namespace: '{0}'.";
+public const string UnknownXmlType = @"Unknown XML type: '{0}'.";
+public const string WriteBufferOverflow = @"Write buffer overflow.";
+public const string WriteNotSupportedOnStream = @"Write operation is not supported on this '{0}' Stream.";
+public const string XmlCanonicalizationNotStarted = @"XML canonicalization was not started.";
+public const string XmlCanonicalizationStarted = @"XML canonicalization started";
+public const string XmlMaxArrayLengthOrMaxItemsQuotaExceeded = @"XML max array length or max items quota exceeded. It must be less than {0}.";
+public const string XmlMaxBytesPerReadExceeded = @"XML max bytes per read exceeded. It must be less than {0}.";
+public const string XmlMaxDepthExceeded = @"XML max depth exceeded. It must be less than {0}.";
+public const string XmlMaxStringContentLengthExceeded = @"XML max string content length exceeded. It must be less than {0}.";
+public const string XmlObjectAssignedToIncompatibleInterface = @"Object of type '{0}' is assigned to an incompatible interface '{1}'.";
+
+#endregion
+       }
+}
diff --git a/mcs/class/System.Runtime.Serialization/ReferenceSources/SR_missing.cs b/mcs/class/System.Runtime.Serialization/ReferenceSources/SR_missing.cs
deleted file mode 100644 (file)
index 972c50a..0000000
+++ /dev/null
@@ -1,291 +0,0 @@
-namespace System.Runtime.Serialization
-{
-       static partial class SR
-       {
-
-#region MissingInStrings.txt
-
-//
-// This was retrieved as follows:
-//
-// 1. mcs ReferenceSources/SR.cs -t:library -out:existing.dll
-// 2. mcs {https://raw.githubusercontent.com/mono/mono/wip-serialization-halfway/mcs/class/System.Runtime.Serialization/ReferenceSource/SR.cs} -t:library -out:full.dll
-// 3. csharp -e "System.IO.File.WriteAllLines ("existing.txt", System.Reflection.Assembly.ReflectionOnlyLoadFrom ("existing.dll").GetTypes ().SelectMany (t => t.GetFields ()).Select (f => f.Name).ToArray ())"
-// 4. csharp -e "System.IO.File.WriteAllLines ("full.txt", System.Reflection.Assembly.ReflectionOnlyLoadFrom ("full.dll").GetTypes ().SelectMany (t => t.GetFields ()).Select (f => f.Name).ToArray ())"
-// 5. csharp
-//     var existing = System.IO.File.ReadAllLines ("existing.txt");
-//     var full = System.IO.File.ReadAllLines ("full.txt");
-//  var missing = full.Where (f => !existing.Contains (f));
-//  System.IO.File.WriteAllLines ("missing.cs", missing.Select (m => "public const string " + m + " = @\"" + m + "\";").ToArray ())
-// 6. copy missing.cs contents here.
-//
-
-public const string AbstractElementNotSupported = @"Abstract element '{0}' is not supported.";
-public const string AbstractTypeNotSupported = @"Abstract type is not supported";
-public const string AmbiguousReferencedCollectionTypes1 = @"Ambiguous collection types were referenced: {0}";
-public const string AmbiguousReferencedCollectionTypes3 = @"In '{0}' element in '{1}' namespace, ambiguous collection types were referenced: {2}";
-public const string AmbiguousReferencedTypes1 = @"Ambiguous types were referenced: {0}";
-public const string AmbiguousReferencedTypes3 = @"In '{0}' element in '{1}' namespace, ambiguous types were referenced: {2}";
-public const string AnnotationAttributeNotFound = @"Annotation attribute was not found: default value annotation is '{0}', type is '{1}' in '{2}' namespace, emit default value is {3}.";
-public const string AnonymousTypeNotSupported = @"Anonymous type is not supported. Type is '{0}' in '{1}' namespace.";
-public const string AnyAttributeNotSupported = @"XML Schema 'any' attribute is not supported";
-public const string ArrayItemFormMustBe = @"For array item, element 'form' must be {0}.";
-public const string ArraySizeAttributeIncorrect = @"Array size attribute is incorrect; must be between {0} and {1}.";
-
-public const string ArrayTypeCannotBeImported = @"Array type cannot be imported for '{0}' in '{1}' namespace: {2}.";
-public const string AssemblyNotFound = @"Assembly '{0}' was not found.";
-public const string AttributeNotFound = @"Attribute was not found for CLR type '{1}' in namespace '{0}'. XML reader node is on {2}, '{4}' node in '{3}' namespace.";
-public const string BaseTypeNotISerializable = @"Base type '{0}' in '{1}' namespace is not ISerializable.";
-public const string CannotComputeUniqueName = @"Cannot compute unique name for '{0}'.";
-public const string CannotDeriveFromSealedReferenceType = @"Cannod drive from sealed reference type '{2}', for '{0}' element in '{1}' namespace.";
-public const string CannotDeserializeForwardedType = @"Cannot deserialize forwarded type '{0}'.";
-public const string CannotExportNullAssembly = @"Cannot export null assembly.";
-public const string CannotExportNullKnownType = @"Cannot export null known type.";
-public const string CannotExportNullType = @"Cannot export null type.";
-public const string CannotHaveDuplicateAttributeNames = @"Cannot have duplicate attribute names '{0}'.";
-public const string CannotHaveDuplicateElementNames = @"Cannot have duplicate element names '{0}'.";
-public const string CannotImportInvalidSchemas = @"Cannot import invalid schemas.";
-public const string CannotImportNullDataContractName = @"Cannot import data contract with null name.";
-public const string CannotImportNullSchema = @"Cannot import from schema list that contains null.";
-public const string CannotSetMembersForReferencedType = @"Cannot set members for already referenced type. Base type is '{0}'.";
-public const string CannotSetNamespaceForReferencedType = @"Cannot set namespace for already referenced type. Base type is '{0}'.";
-public const string CannotUseGenericTypeAsBase = @"For '{0}' in '{1}' namespace, generic type cannot be referenced as the base type.";
-public const string ChangingFullTypeNameNotSupported = @"Changing full type name is not supported. Serialization type name: '{0}', data contract type name: '{1}'.";
-public const string CircularTypeReference = @"Circular type reference was found for '{0}' in '{1}' namespace.";
-public const string ClassDataContractReturnedForGetOnlyCollection = @"For '{0}' type, class data contract was returned for get-only collection.";
-public const string CLRNamespaceMappedMultipleTimes = @"CLR namespace is mapped multiple times. Current data contract namespace is '{0}', found '{1}' for CLR namespace '{2}'.";
-public const string ClrTypeNotFound = @"CLR type '{1}' in assembly '{0}' is not found.";
-public const string CollectionAssignedToIncompatibleInterface = @"Collection of type '{0}' is assigned to an incompatible interface '{1}'";
-public const string ComplexTypeRestrictionNotSupported = @"XML schema complexType restriction is not supported.";
-public const string ConfigDataContractSerializerSectionLoadError = @"Failed to load configuration section for dataContractSerializer.";
-public const string ConfigIndexOutOfRange = @"For type '{0}', configuration index is out of range.";
-public const string ConfigMustOnlyAddParamsWithType = @"Configuration parameter element must only add params with type."; // huh? the code doesn't make a lot of sense to me...
-public const string ConfigMustOnlySetTypeOrIndex = @"Configuration parameter element can set only one of either type or index.";
-public const string ConfigMustSetTypeOrIndex = @"Configuration parameter element must set either type or index.";
-public const string CouldNotReadSerializationSchema = @"Could not read serialization schema for '{0}' namespace.";
-public const string DefaultOnElementNotSupported = @"On element '{0}', default value is not supported.";
-public const string DerivedTypeNotISerializable = @"On type '{0}' in '{1}' namespace, derived type is not ISerializable.";
-public const string DupContractInDataContractSet = @"Duplicate contract in data contract set was found, for '{0}' in '{1}' namespace.";
-public const string DuplicateExtensionDataSetMethod = @"Duplicate extension data set method was found, for method '{0}', existing method is '{1}', on data contract type '{2}'.";
-public const string DupTypeContractInDataContractSet = @"Duplicate type contract in data contract set. Type name '{0}', for data contract '{1}' in '{2}' namespace.";
-public const string ElementMaxOccursMustBe = @"On element '{0}', schema element maxOccurs must be 1.";
-public const string ElementMinOccursMustBe = @"On element '{0}', schema element minOccurs must be less or equal to 1.";
-public const string ElementRefOnLocalElementNotSupported = @"For local element, ref is not supported. The referenced name is '{0}' in '{1}' namespace.";
-public const string EnumEnumerationFacetsMustHaveValue = @"Schema enumeration facet must have values.";
-public const string EnumListInAnonymousTypeNotSupported = @"Enum list in anonymous type is not supported.";
-public const string EnumListMustContainAnonymousType = @"Enum list must contain an anonymous type.";
-public const string EnumOnlyEnumerationFacetsSupported = @"For schema facets, only enumeration is supported.";
-public const string EnumRestrictionInvalid = @"For simpleType restriction, only enum is supported and this type could not be convert to enum.";
-public const string EnumTypeCannotBeImported = @"For '{0}' in '{1}' namespace, enum type cannot be imported: {2}";
-public const string EnumTypeNotSupportedByDataContractJsonSerializer = @"Enum type is not supported by DataContractJsonSerializer. The underlying type is '{0}'.";
-public const string EnumUnionInAnonymousTypeNotSupported = @"Enum union in anonymous type is not supported.";
-public const string ExtensionDataSetMustReturnVoid = @"For type '{0}' method '{1}', extension data set method must return void.";
-public const string ExtensionDataSetParameterInvalid = @"For type '{0}' method '{1}', extension data set method has invalid type of parameter '{2}'.";
-public const string FactoryObjectContainsSelfReference = @"Factory object contains a reference to self. Old object is '{0}', new object is '{1}'.";
-public const string FactoryTypeNotISerializable = @"For data contract '{1}', factory type '{0}' is not ISerializable.";
-public const string FixedOnElementNotSupported = @"On schema element '{0}', fixed value is not supported.";
-public const string FlushBufferAlreadyInUse = @"Flush buffer is already in use.";
-public const string FormMustBeQualified = @"On schema element '{0}', form must be qualified.";
-public const string GenericAnnotationAttributeNotFound = @"On type '{0}' Generic annotation attribute '{1}' was not found.";
-public const string GenericAnnotationForNestedLevelMustBeIncreasing = @"On type '{2}', generic annotation for nested level must be increasing. Argument element is '{0}' in '{1}' namespace.";
-public const string GenericAnnotationHasInvalidAttributeValue = @"On type '{2}', generic annotation has invalid attribute value '{3}'. Argument element is '{0}' in '{1}' namespace. Nested level attribute attribute name is '{4}'. Type is '{5}'."; // dunno if this makes sense...
-public const string GenericAnnotationHasInvalidElement = @"On type '{2}', generic annotation has invalid element. Argument element is '{0}' in '{1}' namespace.";
-public const string GenericTypeNameMismatch = @"Generic type name mismatch. Expected '{0}' in '{1}' namespace, got '{2}' in '{3}' namespace instead.";
-public const string GenericTypeNotExportable = @"Generic type '{0}' is not exportable.";
-public const string GetOnlyCollectionMustHaveAddMethod = @"On type '{0}', get-only collection must have an Add method.";
-public const string GetRealObjectReturnedNull = @"On the surrogate data contract for '{0}', GetRealObject method returned null.";
-public const string InvalidAnnotationExpectingText = @"For annotation element '{0}' in namespace '{1}', expected text but got element '{2}' in '{3}' namespace.";
-public const string InvalidAssemblyFormat = @"'{0}': invalid assembly format.";
-public const string InvalidCharacterEncountered = @"Encountered an invalid character '{0}'.";
-public const string InvalidClassDerivation = @"Invalid class derivation from '{0}' in '{1}' namespace.";
-public const string InvalidClrNameGeneratedForISerializable = @"Invalid CLR name '{2}' is generated for ISerializable type '{0}' in '{1}' namespace.";
-public const string InvalidClrNamespaceGeneratedForISerializable = @"Invalid CLR namespace '{3}' is generated for ISerializable type '{0}' in '{1}' namespace. Data contract namespace from the URI would be generated as '{2}'.";
-public const string InvalidDataNode = @"Invalid data node for '{0}' type.";
-public const string InvalidEmitDefaultAnnotation = @"Invalid EmilDefault annotation for '{0}' in type '{1}' in '{2}' namespace.";
-public const string InvalidEnumBaseType = @"Invalid enum base type is specified for type '{0}' in '{1}' namespace, element name is '{2}' in '{3}' namespace.";
-public const string InvalidISerializableDerivation = @"Invalid ISerializable derivation from '{0}' in '{1}' namespace.";
-public const string InvalidKeyValueType = @"'{0}' is an invalid key value type.";
-public const string InvalidKeyValueTypeNamespace = @"'{0}' in '{1}' namespace is an invalid key value type.";
-public const string InvalidReturnSchemaOnGetSchemaMethod = @"On type '{0}', the return value from GetSchema method was invalid.";
-public const string InvalidStateInExtensionDataReader = @"Invalid state in extension data reader.";
-public const string InvalidXmlDeserializingExtensionData = @"Invalid XML while deserializing extension data.";
-public const string IsAnyNotSupportedByNetDataContractSerializer = @"For type '{0}', IsAny is not supported by NetDataContractSerializer.";
-public const string IsDictionaryFormattedIncorrectly = @"IsDictionary formatted value '{0}' is incorrect: {1}";
-public const string ISerializableAssemblyNameSetToZero = @"ISerializable AssemblyName is set to ""0"" for type '{0}'.";
-public const string ISerializableCannotHaveDataContract = @"ISerializable type '{0}' cannot have DataContract.";
-public const string ISerializableContainsMoreThanOneItems = @"ISerializable cannot contain more than one item.";
-public const string ISerializableDerivedContainsOneOrMoreItems = @"Type derived from ISerializable cannot contain more than one item.";
-public const string ISerializableDoesNotContainAny = @"ISerializable does not contain any element.";
-public const string ISerializableMustRefFactoryTypeAttribute = @"ISerializable must have ref attribute that points to its factory type.";
-public const string ISerializableTypeCannotBeImported = @"ISerializable type '{0}' in '{1}' namespace cannot be imported: {2}";
-public const string ISerializableWildcardMaxOccursMustBe = @"ISerializable wildcard maxOccurs must be '{0}'.";
-public const string ISerializableWildcardMinOccursMustBe = @"ISerializable wildcard maxOccurs must be '{0}'.";
-public const string ISerializableWildcardNamespaceInvalid = @"ISerializable wildcard namespace is invalid: '{0}'.";
-public const string ISerializableWildcardProcessContentsInvalid = @"ISerializable wildcard processContents is invalid: '{0}'.";
-public const string IsReferenceGetOnlyCollectionsNotSupported = @"On type '{1}', attribute '{0}' points to get-only collection, which is not supported.";
-public const string IsValueTypeFormattedIncorrectly = @"IsValueType is formatted incorrectly as '{0}': {1}";
-public const string JsonAttributeAlreadyWritten = @"JSON attribute '{0}' is already written.";
-public const string JsonAttributeMustHaveElement = @"JSON attribute must have an owner element.";
-public const string JsonCannotWriteStandaloneTextAfterQuotedText = @"JSON writer cannot write standalone text after quoted text.";
-public const string JsonCannotWriteTextAfterNonTextAttribute = @"JSON writer cannot write text after non-text attribute. Data type is '{0}'.";
-public const string JsonDateTimeOutOfRange = @"JSON DateTime is out of range.";
-public const string JsonDuplicateMemberInInput = @"Duplicate member '{0}' is found in JSON input.";
-public const string JsonDuplicateMemberNames = @"Duplicate member, including '{1}', is found in JSON input, in type '{0}'.";
-public const string JsonEncodingNotSupported = @"JSON Encoding is not supported.";
-public const string JsonEncounteredUnexpectedCharacter = @"Encountered an unexpected character '{0}' in JSON.";
-public const string JsonEndElementNoOpenNodes = @"Encountered an end element while there was no open element in JSON writer.";
-public const string JsonExpectedEncoding = @"Expected encoding '{0}', got '{1}' instead.";
-public const string JsonInvalidBytes = @"Invalid bytes in JSON.";
-public const string JsonInvalidDataTypeSpecifiedForServerType = @"The specified data type is invalid for server type. Type: '{0}', specified data type: '{1}', server type: '{2}', object '{3}'."; // I wonder if this makes sense...
-public const string JsonInvalidDateTimeString = @"Invalid JSON dateTime string is specified: original value '{0}', start guide writer: {1}, end guard writer: {2}.";
-public const string JsonInvalidFFFE = @"FFFE in JSON is invalid.";
-public const string JsonInvalidItemNameForArrayElement = @"Invalid JSON item name '{0}' for array element (item element is '{1}' in JSON).";
-public const string JsonInvalidLocalNameEmpty = @"Empty string is invalid as a local name.";
-public const string JsonInvalidMethodBetweenStartEndAttribute = @"Invalid method call state between start and end attribute.";
-public const string JsonInvalidRootElementName = @"Invalid root element name '{0}' (root element is '{1}' in JSON).";
-public const string JsonInvalidStartElementCall = @"Invalid call to JSON WriteStartElement method.";
-public const string JsonInvalidWriteState = @"Invalid write state {1} for '{0}' method.";
-public const string JsonMethodNotSupported = @"Method {0} is not supported in JSON.";
-public const string JsonMultipleRootElementsNotAllowedOnWriter = @"Multiple root element is not allowed on JSON writer.";
-public const string JsonMustSpecifyDataType = @"On JSON writer data type '{0}' must be specified. Object string is '{1}', server type string is '{2}'.";
-public const string JsonMustUseWriteStringForWritingAttributeValues = @"On JSON writer WriteString must be used for writing attribute values.";
-public const string JsonNamespaceMustBeEmpty = @"JSON namespace is specified as '{0}' but it must be empty.";
-public const string JsonNestedArraysNotSupported = @"Nested array is not supported in JSON: '{0}'";
-public const string JsonNodeTypeArrayOrObjectNotSpecified = @"Either Object or Array of JSON node type must be specified.";
-public const string JsonNoMatchingStartAttribute = @"WriteEndAttribute was called while there is no open attribute.";
-public const string JsonOffsetExceedsBufferSize = @"On JSON writer, offset exceeded buffer size {0}.";
-public const string JsonOneRequiredMemberNotFound = @"Required member {1} in type '{0}' is not found.";
-public const string JsonOnlyWhitespace = @"Only whitespace characters are allowed for {1} method. The specified value is '{0}'";
-public const string JsonOpenAttributeMustBeClosedFirst = @"JSON attribute must be closed first before calling {0} method.";
-public const string JsonPrefixMustBeNullOrEmpty = @"JSON prefix must be null or empty. '{0}' is specified instead.";
-public const string JsonRequiredMembersNotFound = @"Required members {0} in type '{1}' are not found.";
-public const string JsonServerTypeSpecifiedForInvalidDataType = @"Server type is specified for invalid data type in JSON. Server type: '{0}', type: '{1}', dataType: '{2}', object: '{3}'.";
-public const string JsonSizeExceedsRemainingBufferSpace = @"JSON size exceeded remaining buffer space, by {0} byte(s).";
-public const string JsonTypeNotSupportedByDataContractJsonSerializer = @"Type '{0}' is not suppotred by DataContractJsonSerializer.";
-public const string JsonUnexpectedAttributeLocalName = @"Unexpected attribute local name '{0}'.";
-public const string JsonUnexpectedAttributeValue = @"Unexpected attribute value '{0}'.";
-public const string JsonUnexpectedEndOfFile = @"Unexpected end of file in JSON.";
-public const string JsonUnsupportedForIsReference = @"Unsupported value for IsReference for type '{0}', IsReference value is {1}.";
-public const string JsonWriteArrayNotSupported = @"JSON WriteArray is not supported.";
-public const string JsonWriterClosed = @"JSON writer is already closed.";
-public const string JsonXmlInvalidDeclaration = @"Attempt to write invalid XML declration.";
-public const string JsonXmlProcessingInstructionNotSupported = @"processing instruction is not supported in JSON writer.";
-public const string KeyTypeCannotBeParsedInSimpleDictionary = @"Key type '{1}' for collection type '{0}' cannot be parsed in simple dictionary.";
-public const string KnownTypeConfigGenericParamMismatch = @"Generic parameter count do not match between known type and configuration. Type is '{0}', known type has {1} parameters, configuration has {2} parameters.";
-public const string KnownTypeConfigIndexOutOfBounds = @"For known type configuration, index is out of bound. Root type: '{0}' has {1} type arguments, and index was {2}.";
-public const string KnownTypeConfigIndexOutOfBoundsZero = @"For known type configuration, index is out of bound. Root type: '{0}' has {1} type arguments, and index was {2}.";
-public const string KnownTypeConfigObject = @"Known type configuration specifies System.Object.";
-public const string MaxMimePartsExceeded = @"MIME parts number exceeded the maximum settings. Must be less than {0}. Specified as '{1}'.";
-public const string MimeContentTypeHeaderInvalid = @"MIME content type header is invalid.";
-public const string MimeHeaderInvalidCharacter = @"MIME header has an invalid character ('{0}', {1} in hexadecimal value).";
-public const string MimeMessageGetContentStreamCalledAlready = @"On MimeMessage, GetContentStream method is already called.";
-public const string MimeReaderHeaderAlreadyExists = @"MIME header '{0}' already exists.";
-public const string MimeReaderMalformedHeader = @"Malformed MIME header.";
-public const string MimeReaderResetCalledBeforeEOF = @"On MimeReader, Reset method is called before EOF.";
-public const string MimeReaderTruncated = @"MIME parts are truncated.";
-public const string MimeVersionHeaderInvalid = @"MIME version header is invalid.";
-public const string MimeWriterInvalidStateForClose = @"MIME writer is at invalid state for closing.";
-public const string MimeWriterInvalidStateForContent = @"MIME writer is at invalid state for content.";
-public const string MimeWriterInvalidStateForHeader = @"MIME writer is at invalid state for header.";
-public const string MimeWriterInvalidStateForStartPart = @"MIME writer is at invalid state for starting a part.";
-public const string MimeWriterInvalidStateForStartPreface = @"MIME writer is at invalid state for starting preface.";
-public const string MissingSchemaType = @"Schema type '{0}' is missing and required for '{1}' type.";
-public const string MixedContentNotSupported = @"Mixed content is not supported.";
-public const string MtomBoundaryInvalid = @"MIME boundary is invalid: '{0}'.";
-public const string MtomBufferQuotaExceeded = @"MTOM buffer quota exceeded. The maximum size is {0}.";
-public const string MtomContentTransferEncodingNotPresent = @"MTOM content transfer encoding is not present. ContentTransferEncoding header is '{0}'.";
-public const string MtomContentTransferEncodingNotSupported = @"MTOM content transfer encoding value is not supported. Raw value is '{0}', '{1}' in 7bit encoding, '{2}' in 8bit encoding, and '{3}' in binary.";
-public const string MtomContentTypeInvalid = @"MTOM content type is invalid.";
-public const string MtomDataMustNotContainXopInclude = @"MTOM data must not contain xop:Include element. '{0}' element in '{1}' namespace.";
-public const string MtomExceededMaxSizeInBytes = @"MTOM exceeded max size in bytes. The maximum size is {0}.";
-public const string MtomInvalidCIDUri = @"Invalid MTOM CID URI: '{0}'.";
-public const string MtomInvalidEmptyURI = @"empty URI is invalid for MTOM MIME part.";
-public const string MtomInvalidStartUri = @"Invalid MTOM start URI: '{0}'.";
-public const string MtomInvalidTransferEncodingForMimePart = @"Invalid transfer encoding for MIME part: '{0}', in binary: '{1}'.";
-public const string MtomMessageContentTypeNotFound = @"MTOM message content type was not found.";
-public const string MtomMessageInvalidContent = @"MTOM message content is invalid.";
-public const string MtomMessageInvalidContentInMimePart = @"MTOM message content in MIME part is invalid.";
-public const string MtomMessageInvalidMimeVersion = @"MTOM message has invalid MIME version. Expected '{1}', got '{0}' instead.";
-public const string MtomMessageNotApplicationXopXml = @"MTOM msssage type is not '{0}'.";
-public const string MtomMessageNotMultipart = @"MTOM message is not multipart: media type should be '{0}', media subtype should be '{1}'.";
-public const string MtomMessageRequiredParamNotSpecified = @"Required MTOM parameter '{0}' is not specified.";
-public const string MtomMimePartReferencedMoreThanOnce = @"Specified MIME part '{0}' is referenced more than once.";
-public const string MtomPartNotFound = @"MTOM part with URI '{0}' is not found.";
-public const string MtomRootContentTypeNotFound = @"MTOM root content type is not found.";
-public const string MtomRootNotApplicationXopXml = @"MTOM root should have media type '{0}' and subtype '{1}'.";
-public const string MtomRootPartNotFound = @"MTOM root part is not found.";
-public const string MtomRootRequiredParamNotSpecified = @"Required MTOM root parameter '{0}' is not specified.";
-public const string MtomRootUnexpectedCharset = @"Unexpected charset on MTOM root. Expected '{1}', got '{0}' instead.";
-public const string MtomRootUnexpectedType = @"Unexpected type on MTOM root. Expected '{1}', got '{0}' instead.";
-public const string MtomXopIncludeHrefNotSpecified = @"xop Include element did not specify '{0}' attribute.";
-public const string MtomXopIncludeInvalidXopAttributes = @"xop Include element has invalid attribute: '{0}' in '{1}' namespace.";
-public const string MtomXopIncludeInvalidXopElement = @"xop Include element has invalid element: '{0}' in '{1}' namespace.";
-public const string MustContainOnlyLocalElements = @"Only local elements can be imported.";
-public const string NoAsyncWritePending = @"No async write operation is pending.";
-public const string NonOptionalFieldMemberOnIsReferenceSerializableType = @"For type '{0}', non-optional field member '{1}' is on the Serializable type that has IsReference as {2}.";
-public const string OnlyDataContractTypesCanHaveExtensionData = @"On '{0}' type, only DataContract types can have extension data.";
-public const string PartialTrustISerializableNoPublicConstructor = @"Partial trust access required for the constructor on the ISerializable type '{0}'";
-public const string QueryGeneratorPathToMemberNotFound = @"The path to member was not found for XPath query generator.";
-public const string ReadNotSupportedOnStream = @"Read operation is not supported on the Stream.";
-public const string ReadOnlyClassDeserialization = @"Error on deserializing read-only members in the class: {0}";
-public const string ReadOnlyCollectionDeserialization = @"Error on deserializing read-only collection: {0}";
-public const string RecursiveCollectionType = @"Type '{0}' involves recursive collection.";
-public const string RedefineNotSupported = @"XML Schema 'redefine' is not supported.";
-public const string ReferencedBaseTypeDoesNotExist = @"Referenced base type does not exist. Data contract name: '{0}' in '{1}' namespace, expected type: '{2}' in '{3}' namespace. Collection can be '{4}' or '{5}'."; // is it the expected message? I'm quite unsure.
-public const string ReferencedCollectionTypesCannotContainNull = @"Referenced collection types cannot contain null.";
-public const string ReferencedTypeDoesNotMatch = @"Referenced type '{0}' does not match the expected type '{1}' in '{2}' namespace.";
-public const string ReferencedTypeMatchingMessage = @"Reference type matches.";
-public const string ReferencedTypeNotMatchingMessage = @"Reference type does not match.";
-public const string ReferencedTypesCannotContainNull = @"Referenced types cannot contain null.";
-public const string RequiresClassDataContractToSetIsISerializable = @"To set IsISerializable, class data cotnract is required.";
-public const string RootParticleMustBeSequence = @"Root particle must be sequence to be imported.";
-public const string RootSequenceMaxOccursMustBe = @"On root sequence, maxOccurs must be 1.";
-public const string RootSequenceMustBeRequired = @"Root sequence must have an item and minOccurs must be 1.";
-public const string SeekNotSupportedOnStream = @"Seek operation is not supported on this Stream.";
-public const string SerializationInfo_ConstructorNotFound = @"Constructor that takes SerializationInfo and StreamingContext is not found for '{0}'.";
-public const string SimpleContentNotSupported = @"Simple content is not supported.";
-public const string SimpleTypeRestrictionDoesNotSpecifyBase = @"This simpleType restriction does not specify the base type.";
-public const string SimpleTypeUnionNotSupported = @"simpleType union is not supported.";
-public const string SpecifiedTypeNotFoundInSchema = @"Specified type '{0}' in '{1}' namespace is not found in the schemas.";
-public const string SubstitutionGroupOnElementNotSupported = @"substitutionGroups on elements are not supported.";
-public const string SurrogatesWithGetOnlyCollectionsNotSupported = @"Surrogates with get-only collections are not supported. Type '{1}' contains '{2}' which is of '{0}' type.";
-public const string SurrogatesWithGetOnlyCollectionsNotSupportedSerDeser = @"Surrogates with get-only collections are not supported. Found on type '{0}'.";
-public const string TopLevelElementRepresentsDifferentType = @"Top-level element represents a different type. Expected '{0}' type in '{1}' namespace.";
-public const string TraceCodeElementIgnored = @"Element ignored";
-public const string TraceCodeFactoryTypeNotFound = @"Factory type not found";
-public const string TraceCodeObjectWithLargeDepth = @"Object with large depth";
-public const string TraceCodeReadObjectBegin = @"ReadObject begins";
-public const string TraceCodeReadObjectEnd = @"ReadObject ends";
-public const string TraceCodeWriteObjectBegin = @"WriteObject begins";
-public const string TraceCodeWriteObjectContentBegin = @"WriteObjectContent begins";
-public const string TraceCodeWriteObjectContentEnd = @"WriteObjectContent ends";
-public const string TraceCodeWriteObjectEnd = @"WriteObject ends";
-public const string TraceCodeXsdExportAnnotationFailed = @"XSD export annotation failed";
-public const string TraceCodeXsdExportBegin = @"XSD export begins";
-public const string TraceCodeXsdExportDupItems = @"XSD export duplicate items";
-public const string TraceCodeXsdExportEnd = @"XSD export ends";
-public const string TraceCodeXsdExportError = @"XSD export error";
-public const string TraceCodeXsdImportAnnotationFailed = @"XSD import annotation failed";
-public const string TraceCodeXsdImportBegin = @"XSD import begins";
-public const string TraceCodeXsdImportEnd = @"XSD import ends";
-public const string TraceCodeXsdImportError = @"XSD import error";
-public const string TypeCannotBeForwardedFrom = @"Type '{0}' in assembly '{1}' cannot be forwarded from assembly '{2}'.";
-public const string TypeCannotBeImported = @"Type '{0}' in '{1}' namespace cannot be imported: {2}";
-public const string TypeCannotBeImportedHowToFix = @"Type cannot be imported: {0}"; // I cannot see where HowToFix is given from...
-public const string TypeHasNotBeenImported = @"Type '{0}' in '{1}' namespace has not been imported.";
-public const string TypeMustBeIXmlSerializable = @"Type '{0}' must be IXmlSerializable. Contract type: '{1}', contract name: '{2}' in '{3}' namespace.";
-public const string TypeShouldNotContainAttributes = @"Type should not contain attributes. Serialization namespace: '{0}'.";
-public const string UnknownXmlType = @"Unknown XML type: '{0}'.";
-public const string WriteBufferOverflow = @"Write buffer overflow.";
-public const string WriteNotSupportedOnStream = @"Write operation is not supported on this '{0}' Stream.";
-public const string XmlCanonicalizationNotStarted = @"XML canonicalization was not started.";
-public const string XmlCanonicalizationStarted = @"XML canonicalization started";
-public const string XmlMaxArrayLengthOrMaxItemsQuotaExceeded = @"XML max array length or max items quota exceeded. It must be less than {0}.";
-public const string XmlMaxBytesPerReadExceeded = @"XML max bytes per read exceeded. It must be less than {0}.";
-public const string XmlMaxDepthExceeded = @"XML max depth exceeded. It must be less than {0}.";
-public const string XmlMaxStringContentLengthExceeded = @"XML max string content length exceeded. It must be less than {0}.";
-public const string XmlObjectAssignedToIncompatibleInterface = @"Object of type '{0}' is assigned to an incompatible interface '{1}'.";
-
-#endregion
-       }
-}
index fdbcc77c5ba9a9dd2165481724d0e3d2285a8745..f0b6d8d669a1ad8d38cbc385a3bb10d92bf16376 100644 (file)
@@ -507,11 +507,15 @@ namespace System.Runtime.Serialization
                                                } else {
                                                        var typeHandleValue = Type.GetTypeHandle (memberValue);
                                                        var isDeclaredType = typeHandleValue.Equals (CodeInterpreter.ConvertValue (memberValue, memberType, Globals.TypeOfObject));
-                                                       if (isNullableOfT)
+                                                       if (isNullableOfT) {
                                                                ctx.InternalSerialize (writer, memberValue, isDeclaredType, writeXsiType, DataContract.GetId (memberType.TypeHandle), memberType.TypeHandle);
-                                                       else
-                                                               ctx.InternalSerializeReference (writer, memberValue, isDeclaredType, writeXsiType, DataContract.GetId (memberType.TypeHandle), memberType.TypeHandle);                                                          
-                                                       //InternalSerialize((isNullableOfT ? XmlFormatGeneratorStatics.InternalSerializeMethod : XmlFormatGeneratorStatics.InternalSerializeReferenceMethod), () => memberValue, memberType, writeXsiType);
+                                                       } else if (memberType == Globals.TypeOfObject) {
+                                                               var dataContract = DataContract.GetDataContract (memberValue.GetType());
+                                                               writer.WriteAttributeQualifiedName (Globals.XsiPrefix, DictionaryGlobals.XsiTypeLocalName, DictionaryGlobals.SchemaInstanceNamespace, dataContract.Name, dataContract.Namespace);
+                                                               ctx.InternalSerializeReference (writer, memberValue, false, false, -1, typeHandleValue);
+                                                       } else {
+                                                               ctx.InternalSerializeReference (writer, memberValue, isDeclaredType, writeXsiType, DataContract.GetId (memberType.TypeHandle), memberType.TypeHandle);
+                                                       }
                                                }
                                        }
                                }
index 63c072d99e9386e2e103b8fe8650c14f1df12426..9e790d522b7eeae84c83c918ccb91584bed7e9fc 100644 (file)
@@ -5,7 +5,7 @@ Assembly/AssemblyInfo.cs
 ReferenceSources/DiagnosticUtility.cs
 ReferenceSources/FxTrace.cs
 ReferenceSources/SR.cs
-ReferenceSources/SR_missing.cs
+ReferenceSources/SR.missing.cs
 ReferenceSources/XmlExceptionHelper.cs
 
 ReferenceSources/BitFlagsGenerator.cs
index b0c9706a1dbdd42ab798bdfcf4cfebe807e8ef57..547733453e01d33328e916ef748bc572767657f9 100644 (file)
@@ -15,6 +15,7 @@ System.Runtime.Serialization/DataContractSerializerTest_NullableWithDictionary.c
 System.Runtime.Serialization/DataContractSerializerTest_InvalidCharacters.cs
 System.Runtime.Serialization/DataContractSerializerTest_ISerializable.cs
 System.Runtime.Serialization/DataContractSerializerTest.cs
+System.Runtime.Serialization/Exceptions.cs
 System.Runtime.Serialization/KnownTypeAttributeTest.cs
 System.Runtime.Serialization/XmlObjectSerializerTest.cs
 System.Runtime.Serialization/XsdDataContractExporterTest.cs
index ada461fe2b8610290a5e9ef17a4170552cfd21e9..89c0bef1b557867cea18843de713a736cb4fd0e5 100644 (file)
@@ -122,5 +122,17 @@ namespace MonoTests.System.Runtime.Serialization
                                Assert.IsTrue (s.Contains ("<Flags>All</Flags>"));
                        }
                }
+
+               // Bug #37116
+               [Test]
+               public void KeyPairOfAny ()
+               {
+                       var dict = new Dictionary<string, object> ();
+                       dict.Add ("test", new List<string> () { "test entry" });
+
+                       var dcs = new DataContractSerializer (typeof(Dictionary<string, object>));
+                       dcs.WriteObject (new MemoryStream (), dict);
+                       // Should not throw exception.
+               }
        }
 }
diff --git a/mcs/class/System.Runtime.Serialization/Test/System.Runtime.Serialization/Exceptions.cs b/mcs/class/System.Runtime.Serialization/Test/System.Runtime.Serialization/Exceptions.cs
new file mode 100644 (file)
index 0000000..4303c6c
--- /dev/null
@@ -0,0 +1,95 @@
+//
+// Exceptions
+//
+// Authors:
+//      Andi McClure (andi.mcclure@xamarin.com)
+//
+// Copyright 2016 Xamarin Inc. (http://www.xamarin.com)
+//
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.IO;
+using System.Runtime.Serialization;
+using System.Runtime.Serialization.Formatters.Binary;
+using NUnit.Framework;
+
+namespace MonoTests.System.Runtime.Serialization
+{
+       [TestFixture]
+       public class Exceptions
+       {
+               [Serializable]
+               public class SerializableException : Exception
+               {
+                       public string Data;
+
+                       public SerializableException (string data) {
+                               Data = data;
+
+                               SerializeObjectState += HandleSerialization;
+                       }
+
+                       private static void HandleSerialization (object exception, SafeSerializationEventArgs eventArgs) {
+                               eventArgs.AddSerializedState (new SerializableExceptionState (exception));
+                       }
+
+                       [Serializable]
+                       private class SerializableExceptionState : ISafeSerializationData {
+                               private string Data;
+
+                               public SerializableExceptionState (object _exception) {
+                                       SerializableException exception = (SerializableException)_exception;
+
+                                       Data = exception.Data;
+                               }
+
+                               public void CompleteDeserialization (object _exception) {
+                                       SerializableException exception = (SerializableException)_exception;
+                                       exception.SerializeObjectState += HandleSerialization;
+
+                                       exception.Data = Data;
+                               }
+                       }
+               }
+
+               // Effectively tests SerializeObjectState handler support on System.Exception
+               [Test]
+               public void Exception_SerializeObjectState () {
+                       SerializableException exception = new SerializableException ("success");
+                       SerializableException deserializedException;
+                       BinaryFormatter binaryFormatter = new BinaryFormatter ();
+
+                       using (MemoryStream memoryStream = new MemoryStream ())
+                       {
+                               binaryFormatter.Serialize (memoryStream, exception);
+                               memoryStream.Flush ();
+
+                               memoryStream.Seek (0, SeekOrigin.Begin);
+
+                               deserializedException = (SerializableException)binaryFormatter.Deserialize (memoryStream);
+                       }
+
+                       Assert.AreEqual ("success", deserializedException.Data);
+               }
+       }
+}
\ No newline at end of file
index 03e2493cc2606e41cabdaa5cabc0fbfb26db05f0..5c009acb56608c1d391e86faea97071af7e3f33e 100644 (file)
@@ -3,13 +3,12 @@ SUBDIRS =
 include ../../build/rules.make
 
 LIBRARY = System.Security.dll
-LIB_REFS = System System.Xml Mono.Security
+LIB_REFS = secxml/System bare/System.Xml Mono.Security
 LIB_MCS_FLAGS = -nowarn:618 \
        -d:SECURITY_DEP \
-       -r:$(corlib) \
        -nowarn:414
 
-LOCAL_MCS_FLAGS = -lib:$(secxml_libdir) -lib:$(bare_libdir)
+LOCAL_MCS_FLAGS =
 
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:168,169,183,219,414
 
index ad7f73f1b92be950c3c6236ff50567dab61271f9..2be1563c1d7fe3fcd25604e4bbcefd2b6a3489fc 100644 (file)
@@ -4,14 +4,13 @@ include ../../build/rules.make
 
 LIBRARY = System.ServiceModel.Activation.dll
 
-LIB_REFS = System.Core System System.ServiceModel
+LIB_REFS = System.Core System plainservice/System.ServiceModel
 LIB_MCS_FLAGS =
 
-TEST_MCS_FLAGS = -r:System.dll -r:System.Core.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Core
 
-plainservicemodel_dir = $(the_libdir_base)plainservice
-servicemodel = $(plainservicemodel_dir)/System.ServiceModel.dll
-LOCAL_MCS_FLAGS = -lib:$(plainservicemodel_dir)
+servicemodel = $(the_libdir_base)plainservice/System.ServiceModel.dll
 
 include ../../build/library.make
 
index 75422d19e74fbd15a21aa447024b116fd0fdb180..d46df268454428326dff800cee795250cb365896 100644 (file)
@@ -8,8 +8,7 @@ LIB_MCS_FLAGS =
 
 ifneq (2.1, $(FRAMEWORK_VERSION))
 LIB_REFS += System.Configuration
-LIB_MCS_FLAGS += -d:NET_3_5 -d:NET_3_0         \
-                       -r:System.Configuration.dll
+LIB_MCS_FLAGS += -d:NET_3_5 -d:NET_3_0 
 endif
 
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
index ad9a78e6a60c6f2c9a67566f26c10a6c286d2152..f8d30f60025f57b042f907851c4feef3c5be7019 100644 (file)
@@ -8,8 +8,7 @@ LIB_MCS_FLAGS =
 
 ifneq (2.1, $(FRAMEWORK_VERSION))
 LIB_REFS += System.Configuration
-LIB_MCS_FLAGS += -d:NET_3_5 -d:NET_3_0         \
-                       -r:System.Configuration.dll
+LIB_MCS_FLAGS += -d:NET_3_5 -d:NET_3_0
 endif
 
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
index 03dbd5fd9e59d7fd8b5b225e7ed63040f22fc059..5f09e6a23292aadd8f61059dbe303d53c118bc57 100644 (file)
@@ -34,7 +34,8 @@ activation = $(the_libdir_base)System.ServiceModel.Activation.dll
 servicemodel_deps = $(activation)
 
 ifneq (plainservice/,$(intermediate))
-LIB_MCS_FLAGS += -define:HAS_ACTIVATION -r:System.ServiceModel.Activation.dll
+LIB_REFS += System.ServiceModel.Activation
+LIB_MCS_FLAGS += -define:HAS_ACTIVATION
 endif 
 endif # NO_SYSTEM_SERVICEMODEL_ACTIVATION_DEPENDENCY
 
index 361a049e6e6e49b5881ca613e00f9e51d5c201d3..862830b0c76eb927a2b38a78c9b321365f3b2440 100644 (file)
@@ -65,7 +65,6 @@ namespace System.ServiceModel
                        return new EndpointAddress10 (address);
                }
 
-#if !NET_2_1
                public static XmlQualifiedName GetSchema (XmlSchemaSet xmlSchemaSet)
                {
                        if (xmlSchemaSet == null)
@@ -73,7 +72,6 @@ namespace System.ServiceModel
                        xmlSchemaSet.Add (XmlSchema.Read (typeof (EndpointAddress10).Assembly.GetManifestResourceStream ("ws-addr.xsd"), null));
                        return new XmlQualifiedName ("EndpointReferenceType", AddressingVersion.WSAddressing10.Namespace);
                }
-#endif
 
                public EndpointAddress ToEndpointAddress ()
                {
index 0cde2c9bdec8b0b276078978bc3ed79db1fe8434..dd2dc7f1c70d6e37264ac1c428b2d6592f37eacf 100644 (file)
@@ -166,6 +166,7 @@ System.ServiceModel.Security/SupportingTokenParametersTest.cs
 System.ServiceModel.Security/TransportSecurityBindingElementTest.cs
 System.ServiceModel.Security/WSSecurityTokenSerializerTest.cs
 System.ServiceModel/BasicHttpBindingTest.cs
+System.ServiceModel/Bug36080Test.cs
 System.ServiceModel/CallbackBehaviorAttributeTest.cs
 System.ServiceModel/ChannelFactoryTest.cs
 System.ServiceModel/ChannelFactory_1Test.cs
diff --git a/mcs/class/System.ServiceModel/Test/System.ServiceModel/Bug36080Test.cs b/mcs/class/System.ServiceModel/Test/System.ServiceModel/Bug36080Test.cs
new file mode 100644 (file)
index 0000000..2727915
--- /dev/null
@@ -0,0 +1,585 @@
+//
+// Author:
+//       Marcos Henrich <marcos.henrich@xamarin.com>
+//
+// Copyright (c) 2016 Xamarin, Inc.
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy
+// of this software and associated documentation files (the "Software"), to deal
+// in the Software without restriction, including without limitation the rights
+// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+// copies of the Software, and to permit persons to whom the Software is
+// furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+// THE SOFTWARE.
+using System;
+using System.Collections.Generic;
+using System.Globalization;
+using System.Linq;
+using System.Runtime.Serialization;
+using System.ServiceModel;
+using System.ServiceModel.Description;
+using System.Threading;
+using System.ServiceModel.Channels;
+using System.Text;
+using NUnit.Framework;
+
+using MonoTests.Helpers;
+
+namespace MonoTests.System.ServiceModel
+{
+       [TestFixture]
+       public class Bug36080
+       {
+               [Test]
+               public void Bug36080Test ()
+               {
+                       int port = NetworkHelpers.FindFreePort ();
+                       var url = "http://localhost:" + port + "/HelloWorldService";
+
+                       TransportBindingElement element = new HttpTransportBindingElement { MaxBufferSize = int.MaxValue, MaxReceivedMessageSize = int.MaxValue };
+                       Binding binding = new CustomBinding(new BindingElement[]
+                               {
+                                       new TextMessageEncodingBindingElement (MessageVersion.Default, Encoding.UTF8),
+                                       element
+                               });
+
+#if !MOBILE
+                       // Init service
+                       ServiceHost serviceHost = new ServiceHost (typeof (HelloWorldServiceImpl), new Uri (url));
+                       serviceHost.AddServiceEndpoint (typeof (IHelloWorldService), binding, string.Empty);
+
+                       serviceHost.Open ();
+#endif
+                       // In Mobile we still run this tests without any server.
+                       // Issue reported in #36080 was occuring before the connections fails.
+                       var wait = new ManualResetEvent (false);
+
+                       Exception error = null;
+                       string result = null;
+
+                       try {
+                               var client = new HelloWorldServiceClient (binding, new EndpointAddress(url));
+                               client.SayHelloToCompleted += delegate (object o, SayHelloToCompletedEventArgs e) {
+                                       try {
+                                               error = e.Error;
+                                               result = e.Error == null ? e.Result : null;
+                                       } finally {
+                                               wait.Set ();
+                                       }
+                               };
+
+                               var str = "Xamarin";
+                               client.SayHelloToAsync(str);
+
+                               Assert.IsTrue (wait.WaitOne (TimeSpan.FromSeconds (20)), "timeout");
+#if MOBILE
+                               if (error.GetType() == typeof(EndpointNotFoundException))
+                                       return;
+#endif
+
+                               Assert.IsNull (error, "#1, inner exception: {0}", error);
+                               Assert.AreEqual (str, result, "#2");
+                       }  finally {
+#if !MOBILE
+                               serviceHost.Close ();
+#endif
+                       }
+               }
+       }
+
+       public class  HelloWorldServiceImpl : IHelloWorldService
+       {
+               Func<string, string> sayHelloToFunc = SayHelloTo;
+
+               static string SayHelloTo (string name)
+               {
+                       return name;
+               }
+
+               public IAsyncResult BeginSayHelloTo(string name, AsyncCallback callback, object asyncState)
+               {
+                       return sayHelloToFunc.BeginInvoke (name, callback, asyncState);
+               }
+               
+               public string EndSayHelloTo(IAsyncResult result) 
+               {
+                       return sayHelloToFunc.EndInvoke(result);
+               }
+               
+               public IAsyncResult BeginGetHelloData(TestXamarin4WCFService.HelloWorldData helloWorldData, AsyncCallback callback, object asyncState)
+               {
+                       return null;
+               }
+
+               public TestXamarin4WCFService.HelloWorldData EndGetHelloData(IAsyncResult result)
+               {
+                       return null;
+               }
+       }
+}
+
+//------------------------------------------------------------------------------
+// <auto-generated>
+//     This code was generated by a tool.
+//     Runtime Version:4.0.30319.18444
+//
+//     Changes to this file may cause incorrect behavior and will be lost if
+//     the code is regenerated.
+// </auto-generated>
+//------------------------------------------------------------------------------
+
+// 
+// This code was auto-generated by SlSvcUtil, version 5.0.61118.0
+// 
+namespace TestXamarin4WCFService
+{
+    using System.Runtime.Serialization;
+    
+    [System.Diagnostics.DebuggerStepThroughAttribute()]
+    [System.CodeDom.Compiler.GeneratedCodeAttribute("System.Runtime.Serialization", "4.0.0.0")]
+    [System.Runtime.Serialization.DataContractAttribute(Name = "HelloWorldData", Namespace = "http://schemas.datacontract.org/2004/07/TestXamarin4WCFService")]
+    public partial class HelloWorldData : object
+    {
+        
+        private string NameField;
+        
+        private bool SayHelloField;
+        
+        [System.Runtime.Serialization.DataMemberAttribute()]
+        public string Name
+        {
+            get
+            {
+                return this.NameField;
+            }
+            set
+            {
+                this.NameField = value;
+            }
+        }
+        
+        [System.Runtime.Serialization.DataMemberAttribute()]
+        public bool SayHello
+        {
+            get
+            {
+                return this.SayHelloField;
+            }
+            set
+            {
+                this.SayHelloField = value;
+            }
+        }
+    }
+}
+
+
+[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "4.0.0.0")]
+[System.ServiceModel.ServiceContractAttribute(ConfigurationName="IHelloWorldService")]
+public interface IHelloWorldService
+{
+    
+    [System.ServiceModel.OperationContractAttribute(AsyncPattern=true, Action="http://tempuri.org/IHelloWorldService/SayHelloTo", ReplyAction="http://tempuri.org/IHelloWorldService/SayHelloToResponse")]
+    System.IAsyncResult BeginSayHelloTo(string name, System.AsyncCallback callback, object asyncState);
+    
+    string EndSayHelloTo(System.IAsyncResult result);
+    
+    [System.ServiceModel.OperationContractAttribute(AsyncPattern=true, Action="http://tempuri.org/IHelloWorldService/GetHelloData", ReplyAction="http://tempuri.org/IHelloWorldService/GetHelloDataResponse")]
+    System.IAsyncResult BeginGetHelloData(TestXamarin4WCFService.HelloWorldData helloWorldData, System.AsyncCallback callback, object asyncState);
+
+    TestXamarin4WCFService.HelloWorldData EndGetHelloData(System.IAsyncResult result);
+}
+
+[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "4.0.0.0")]
+public interface IHelloWorldServiceChannel : IHelloWorldService, System.ServiceModel.IClientChannel
+{
+}
+
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "4.0.0.0")]
+public partial class SayHelloToCompletedEventArgs : System.ComponentModel.AsyncCompletedEventArgs
+{
+    
+    private object[] results;
+    
+    public SayHelloToCompletedEventArgs(object[] results, System.Exception exception, bool cancelled, object userState) : 
+            base(exception, cancelled, userState)
+    {
+        this.results = results;
+    }
+    
+    public string Result
+    {
+        get
+        {
+            base.RaiseExceptionIfNecessary();
+            return ((string)(this.results[0]));
+        }
+    }
+}
+
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "4.0.0.0")]
+public partial class GetHelloDataCompletedEventArgs : System.ComponentModel.AsyncCompletedEventArgs
+{
+    
+    private object[] results;
+    
+    public GetHelloDataCompletedEventArgs(object[] results, System.Exception exception, bool cancelled, object userState) : 
+            base(exception, cancelled, userState)
+    {
+        this.results = results;
+    }
+
+    public TestXamarin4WCFService.HelloWorldData Result
+    {
+        get
+        {
+            base.RaiseExceptionIfNecessary();
+            return ((TestXamarin4WCFService.HelloWorldData)(this.results[0]));
+        }
+    }
+}
+
+[System.Diagnostics.DebuggerStepThroughAttribute()]
+[System.CodeDom.Compiler.GeneratedCodeAttribute("System.ServiceModel", "4.0.0.0")]
+public partial class HelloWorldServiceClient : System.ServiceModel.ClientBase<IHelloWorldService>, IHelloWorldService
+{
+    
+    private BeginOperationDelegate onBeginSayHelloToDelegate;
+    
+    private EndOperationDelegate onEndSayHelloToDelegate;
+    
+    private System.Threading.SendOrPostCallback onSayHelloToCompletedDelegate;
+    
+    private BeginOperationDelegate onBeginGetHelloDataDelegate;
+    
+    private EndOperationDelegate onEndGetHelloDataDelegate;
+    
+    private System.Threading.SendOrPostCallback onGetHelloDataCompletedDelegate;
+    
+    private BeginOperationDelegate onBeginOpenDelegate;
+    
+    private EndOperationDelegate onEndOpenDelegate;
+    
+    private System.Threading.SendOrPostCallback onOpenCompletedDelegate;
+    
+    private BeginOperationDelegate onBeginCloseDelegate;
+    
+    private EndOperationDelegate onEndCloseDelegate;
+    
+    private System.Threading.SendOrPostCallback onCloseCompletedDelegate;
+    
+    public HelloWorldServiceClient()
+    {
+    }
+    
+    public HelloWorldServiceClient(string endpointConfigurationName) : 
+            base(endpointConfigurationName)
+    {
+    }
+    
+    public HelloWorldServiceClient(string endpointConfigurationName, string remoteAddress) : 
+            base(endpointConfigurationName, remoteAddress)
+    {
+    }
+    
+    public HelloWorldServiceClient(string endpointConfigurationName, System.ServiceModel.EndpointAddress remoteAddress) : 
+            base(endpointConfigurationName, remoteAddress)
+    {
+    }
+    
+    public HelloWorldServiceClient(System.ServiceModel.Channels.Binding binding, System.ServiceModel.EndpointAddress remoteAddress) : 
+            base(binding, remoteAddress)
+    {
+    }
+    
+    public System.Net.CookieContainer CookieContainer
+    {
+        get
+        {
+            System.ServiceModel.Channels.IHttpCookieContainerManager httpCookieContainerManager = this.InnerChannel.GetProperty<System.ServiceModel.Channels.IHttpCookieContainerManager>();
+            if ((httpCookieContainerManager != null))
+            {
+                return httpCookieContainerManager.CookieContainer;
+            }
+            else
+            {
+                return null;
+            }
+        }
+        set
+        {
+            System.ServiceModel.Channels.IHttpCookieContainerManager httpCookieContainerManager = this.InnerChannel.GetProperty<System.ServiceModel.Channels.IHttpCookieContainerManager>();
+            if ((httpCookieContainerManager != null))
+            {
+                httpCookieContainerManager.CookieContainer = value;
+            }
+            else
+            {
+                throw new System.InvalidOperationException("Unable to set the CookieContainer. Please make sure the binding contains an HttpC" +
+                        "ookieContainerBindingElement.");
+            }
+        }
+    }
+    
+    public event System.EventHandler<SayHelloToCompletedEventArgs> SayHelloToCompleted;
+    
+    public event System.EventHandler<GetHelloDataCompletedEventArgs> GetHelloDataCompleted;
+    
+    public event System.EventHandler<System.ComponentModel.AsyncCompletedEventArgs> OpenCompleted;
+    
+    public event System.EventHandler<System.ComponentModel.AsyncCompletedEventArgs> CloseCompleted;
+    
+    [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
+    System.IAsyncResult IHelloWorldService.BeginSayHelloTo(string name, System.AsyncCallback callback, object asyncState)
+    {
+        return base.Channel.BeginSayHelloTo(name, callback, asyncState);
+    }
+    
+    [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
+    string IHelloWorldService.EndSayHelloTo(System.IAsyncResult result)
+    {
+        return base.Channel.EndSayHelloTo(result);
+    }
+    
+    private System.IAsyncResult OnBeginSayHelloTo(object[] inValues, System.AsyncCallback callback, object asyncState)
+    {
+        string name = ((string)(inValues[0]));
+        return ((IHelloWorldService)(this)).BeginSayHelloTo(name, callback, asyncState);
+    }
+    
+    private object[] OnEndSayHelloTo(System.IAsyncResult result)
+    {
+        string retVal = ((IHelloWorldService)(this)).EndSayHelloTo(result);
+        return new object[] {
+                retVal};
+    }
+    
+    private void OnSayHelloToCompleted(object state)
+    {
+        if ((this.SayHelloToCompleted != null))
+        {
+            InvokeAsyncCompletedEventArgs e = ((InvokeAsyncCompletedEventArgs)(state));
+            this.SayHelloToCompleted(this, new SayHelloToCompletedEventArgs(e.Results, e.Error, e.Cancelled, e.UserState));
+        }
+    }
+    
+    public void SayHelloToAsync(string name)
+    {
+        this.SayHelloToAsync(name, null);
+    }
+    
+    public void SayHelloToAsync(string name, object userState)
+    {
+        if ((this.onBeginSayHelloToDelegate == null))
+        {
+            this.onBeginSayHelloToDelegate = new BeginOperationDelegate(this.OnBeginSayHelloTo);
+        }
+        if ((this.onEndSayHelloToDelegate == null))
+        {
+            this.onEndSayHelloToDelegate = new EndOperationDelegate(this.OnEndSayHelloTo);
+        }
+        if ((this.onSayHelloToCompletedDelegate == null))
+        {
+            this.onSayHelloToCompletedDelegate = new System.Threading.SendOrPostCallback(this.OnSayHelloToCompleted);
+        }
+        base.InvokeAsync(this.onBeginSayHelloToDelegate, new object[] {
+                    name}, this.onEndSayHelloToDelegate, this.onSayHelloToCompletedDelegate, userState);
+    }
+    
+    [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
+    System.IAsyncResult IHelloWorldService.BeginGetHelloData(TestXamarin4WCFService.HelloWorldData helloWorldData, System.AsyncCallback callback, object asyncState)
+    {
+        return base.Channel.BeginGetHelloData(helloWorldData, callback, asyncState);
+    }
+    
+    [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
+    TestXamarin4WCFService.HelloWorldData IHelloWorldService.EndGetHelloData(System.IAsyncResult result)
+    {
+        return base.Channel.EndGetHelloData(result);
+    }
+    
+    private System.IAsyncResult OnBeginGetHelloData(object[] inValues, System.AsyncCallback callback, object asyncState)
+    {
+        TestXamarin4WCFService.HelloWorldData helloWorldData = ((TestXamarin4WCFService.HelloWorldData)(inValues[0]));
+        return ((IHelloWorldService)(this)).BeginGetHelloData(helloWorldData, callback, asyncState);
+    }
+    
+    private object[] OnEndGetHelloData(System.IAsyncResult result)
+    {
+        TestXamarin4WCFService.HelloWorldData retVal = ((IHelloWorldService)(this)).EndGetHelloData(result);
+        return new object[] {
+                retVal};
+    }
+    
+    private void OnGetHelloDataCompleted(object state)
+    {
+        if ((this.GetHelloDataCompleted != null))
+        {
+            InvokeAsyncCompletedEventArgs e = ((InvokeAsyncCompletedEventArgs)(state));
+            this.GetHelloDataCompleted(this, new GetHelloDataCompletedEventArgs(e.Results, e.Error, e.Cancelled, e.UserState));
+        }
+    }
+
+    public void GetHelloDataAsync(TestXamarin4WCFService.HelloWorldData helloWorldData)
+    {
+        this.GetHelloDataAsync(helloWorldData, null);
+    }
+
+    public void GetHelloDataAsync(TestXamarin4WCFService.HelloWorldData helloWorldData, object userState)
+    {
+        if ((this.onBeginGetHelloDataDelegate == null))
+        {
+            this.onBeginGetHelloDataDelegate = new BeginOperationDelegate(this.OnBeginGetHelloData);
+        }
+        if ((this.onEndGetHelloDataDelegate == null))
+        {
+            this.onEndGetHelloDataDelegate = new EndOperationDelegate(this.OnEndGetHelloData);
+        }
+        if ((this.onGetHelloDataCompletedDelegate == null))
+        {
+            this.onGetHelloDataCompletedDelegate = new System.Threading.SendOrPostCallback(this.OnGetHelloDataCompleted);
+        }
+        base.InvokeAsync(this.onBeginGetHelloDataDelegate, new object[] {
+                    helloWorldData}, this.onEndGetHelloDataDelegate, this.onGetHelloDataCompletedDelegate, userState);
+    }
+    
+    private System.IAsyncResult OnBeginOpen(object[] inValues, System.AsyncCallback callback, object asyncState)
+    {
+        return ((System.ServiceModel.ICommunicationObject)(this)).BeginOpen(callback, asyncState);
+    }
+    
+    private object[] OnEndOpen(System.IAsyncResult result)
+    {
+        ((System.ServiceModel.ICommunicationObject)(this)).EndOpen(result);
+        return null;
+    }
+    
+    private void OnOpenCompleted(object state)
+    {
+        if ((this.OpenCompleted != null))
+        {
+            InvokeAsyncCompletedEventArgs e = ((InvokeAsyncCompletedEventArgs)(state));
+            this.OpenCompleted(this, new System.ComponentModel.AsyncCompletedEventArgs(e.Error, e.Cancelled, e.UserState));
+        }
+    }
+    
+    public void OpenAsync()
+    {
+        this.OpenAsync(null);
+    }
+    
+    public void OpenAsync(object userState)
+    {
+        if ((this.onBeginOpenDelegate == null))
+        {
+            this.onBeginOpenDelegate = new BeginOperationDelegate(this.OnBeginOpen);
+        }
+        if ((this.onEndOpenDelegate == null))
+        {
+            this.onEndOpenDelegate = new EndOperationDelegate(this.OnEndOpen);
+        }
+        if ((this.onOpenCompletedDelegate == null))
+        {
+            this.onOpenCompletedDelegate = new System.Threading.SendOrPostCallback(this.OnOpenCompleted);
+        }
+        base.InvokeAsync(this.onBeginOpenDelegate, null, this.onEndOpenDelegate, this.onOpenCompletedDelegate, userState);
+    }
+    
+    private System.IAsyncResult OnBeginClose(object[] inValues, System.AsyncCallback callback, object asyncState)
+    {
+        return ((System.ServiceModel.ICommunicationObject)(this)).BeginClose(callback, asyncState);
+    }
+    
+    private object[] OnEndClose(System.IAsyncResult result)
+    {
+        ((System.ServiceModel.ICommunicationObject)(this)).EndClose(result);
+        return null;
+    }
+    
+    private void OnCloseCompleted(object state)
+    {
+        if ((this.CloseCompleted != null))
+        {
+            InvokeAsyncCompletedEventArgs e = ((InvokeAsyncCompletedEventArgs)(state));
+            this.CloseCompleted(this, new System.ComponentModel.AsyncCompletedEventArgs(e.Error, e.Cancelled, e.UserState));
+        }
+    }
+    
+    public void CloseAsync()
+    {
+        this.CloseAsync(null);
+    }
+    
+    public void CloseAsync(object userState)
+    {
+        if ((this.onBeginCloseDelegate == null))
+        {
+            this.onBeginCloseDelegate = new BeginOperationDelegate(this.OnBeginClose);
+        }
+        if ((this.onEndCloseDelegate == null))
+        {
+            this.onEndCloseDelegate = new EndOperationDelegate(this.OnEndClose);
+        }
+        if ((this.onCloseCompletedDelegate == null))
+        {
+            this.onCloseCompletedDelegate = new System.Threading.SendOrPostCallback(this.OnCloseCompleted);
+        }
+        base.InvokeAsync(this.onBeginCloseDelegate, null, this.onEndCloseDelegate, this.onCloseCompletedDelegate, userState);
+    }
+    
+    protected override IHelloWorldService CreateChannel()
+    {
+        return new HelloWorldServiceClientChannel(this);
+    }
+    
+    private class HelloWorldServiceClientChannel : ChannelBase<IHelloWorldService>, IHelloWorldService
+    {
+        
+        public HelloWorldServiceClientChannel(System.ServiceModel.ClientBase<IHelloWorldService> client) : 
+                base(client)
+        {
+        }
+        
+        public System.IAsyncResult BeginSayHelloTo(string name, System.AsyncCallback callback, object asyncState)
+        {
+            object[] _args = new object[1];
+            _args[0] = name;
+            System.IAsyncResult _result = base.BeginInvoke("SayHelloTo", _args, callback, asyncState);
+            return _result;
+        }
+        
+        public string EndSayHelloTo(System.IAsyncResult result)
+        {
+            object[] _args = new object[0];
+            string _result = ((string)(base.EndInvoke("SayHelloTo", _args, result)));
+            return _result;
+        }
+
+        public System.IAsyncResult BeginGetHelloData(TestXamarin4WCFService.HelloWorldData helloWorldData, System.AsyncCallback callback, object asyncState)
+        {
+            object[] _args = new object[1];
+            _args[0] = helloWorldData;
+            System.IAsyncResult _result = base.BeginInvoke("GetHelloData", _args, callback, asyncState);
+            return _result;
+        }
+
+        public TestXamarin4WCFService.HelloWorldData EndGetHelloData(System.IAsyncResult result)
+        {
+            object[] _args = new object[0];
+            TestXamarin4WCFService.HelloWorldData _result = ((TestXamarin4WCFService.HelloWorldData)(base.EndInvoke("GetHelloData", _args, result)));
+            return _result;
+        }
+    }
+}
index 349e5c75754d6e3996c58e5041b9253198c7b489..017f1a880c8a371ee9a228c80fe6c8aaebf9991d 100644 (file)
@@ -7,8 +7,9 @@ LIBRARY = System.Threading.Tasks.Dataflow.dll
 include ../../build/library.make
 
 LIB_REFS += System.Core System
-LIB_MCS_FLAGS += -r:$(corlib) -d:CONCURRENT_COLLECTIONS
+LIB_MCS_FLAGS += -d:CONCURRENT_COLLECTIONS
 
-TEST_MCS_FLAGS = -r:System.Core.dll -r:System.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System.Core System
 
 EXTRA_DISTFILES=README.md
index 08e9bd68021ad136a721544c9f3a7366b8dd10cc..07672c10b06da81802b6a3ac7188edce5129ee90 100644 (file)
@@ -5,10 +5,10 @@ include ../../build/rules.make
 LIBRARY = System.Transactions.dll
 ifdef MOBILE_PROFILE
 LIB_REFS = System
-LIB_MCS_FLAGS = /r:$(corlib) /define:MOBILE
+LIB_MCS_FLAGS = /define:MOBILE
 else
 LIB_REFS = System System.Configuration
-LIB_MCS_FLAGS = /r:$(corlib)
+LIB_MCS_FLAGS =
 endif
 
 TEST_MCS_FLAGS = $(LIB_MCS_FLAGS)
index 08cb7d04c2b6c0d14512c03a8f744431da3b33b6..df81a3719ca47c816f3937a33d1e1886bae5831d 100644 (file)
@@ -160,11 +160,11 @@ TEST_RESOURCE_FILES = \
 
 NUNIT_RESOURCE_FILES = $(TEST_RESOURCE_FILES)
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -r:System.ComponentModel.DataAnnotations.dll -r:System.Configuration.dll \
-       $(NUNIT_RESOURCE_FILES:%=/resource:%) -r:SystemWebTestShim.dll -r:System.Xml.dll
+TEST_LIB_REFS = System.ComponentModel.DataAnnotations System.Configuration SystemWebTestShim System.Xml
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(NUNIT_RESOURCE_FILES:%=/resource:%)
 
 ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
-TEST_MCS_FLAGS += -r:System.Web.ApplicationServices.dll
+TEST_LIB_REFS += System.Web.ApplicationServices
 endif
 
 EXTRA_DISTFILES = $(foreach resource,$(TEST_RESOURCE_FILES), $(shell echo $(subst \`,\\\`,$(resource)) | cut -d ',' -f 1))
index bf15f32944f8a2e700ca4acc1066ddedf799497e..4a3f8a48970acbdeb930cc1d3928e8e329f9698f 100644 (file)
@@ -39,7 +39,7 @@ NUNIT_RESOURCE_FILES= \
 CLASSLIB_DIR = $(topdir)/class/lib/$(PROFILE)
 
 STANDALONE_RUNNER_SUPPORT_ASSEMBLY = $(CLASSLIB_DIR)/standalone-runner-support.dll
-STANDALONE_TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -debug:full -r:$(STANDALONE_RUNNER_SUPPORT_ASSEMBLY) -r:System.Web.dll -r:System.Web.Extensions.dll -r:nunit.framework.dll
+STANDALONE_TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -r:$(STANDALONE_RUNNER_SUPPORT_ASSEMBLY) -r:$(topdir)/class/lib/$(PROFILE)/System.Web.dll -r:$(topdir)/class/lib/$(PROFILE)/System.Web.Extensions.dll -r:$(topdir)/class/lib/$(PROFILE)/nunit.framework.dll
 STANDALONE_TEST_ASSEMBLY = System.Web.Extensions_standalone_test_$(PROFILE).dll
 STANDALONE_TEST_MAKEFRAG = $(depsdir)/$(STANDALONE_TEST_ASSEMBLY).makefrag
 
@@ -49,20 +49,20 @@ ifdef TESTNAME
 RUN_STANDALONE += --test=$(TESTNAME)
 endif
 
-ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
-OTHER_LIB_MCS_FLAGS += -r:System.Web.ApplicationServices.dll
-endif
-
 LIB_REFS = System System.Core System.Drawing System.Data System.Data.Linq System.Xml System.Web System.Web.Services System.Configuration System.EnterpriseServices System.ServiceModel
 LIB_MCS_FLAGS = \
        -unsafe \
        -define:NET_3_5                 \
        -define:SYSTEM_WEB_EXTENSIONS   \
-       -r:$(corlib)                    \
        $(OTHER_LIB_MCS_FLAGS)          \
        $(RESOURCE_FILES:%=/resource:%)
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -doc:$(test_lib:.dll=.xml) -nowarn:219,169,1591 $(NUNIT_RESOURCE_FILES:%=/resource:%) -r:SystemWebTestShim.dll -define:SYSTEM_WEB_EXTENSIONS
+ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
+LIB_REFS += System.Web.ApplicationServices
+endif
+
+TEST_LIB_REFS = SystemWebTestShim
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -doc:$(test_lib:.dll=.xml) -nowarn:219,169,1591 $(NUNIT_RESOURCE_FILES:%=/resource:%) -define:SYSTEM_WEB_EXTENSIONS
 
 EXTRA_DISTFILES = $(RESOURCE_FILES_DIST) $(NUNIT_RESOURCE_FILES) \
        System.Web.Extensions_standalone_test.dll.sources \
index 891b1ef66ce35e2bd5bfe39da86555d0efe195e4..29e6cfb92b86bd69a4e665ccb7ab5a94d7cb4732 100644 (file)
@@ -473,22 +473,22 @@ namespace System.Web.Script.Serialization
                                case JsonType.INTEGER:
                                        /* MS AJAX.NET JSON parser promotes big integers to double */
                                        
-                                       if (Int32.TryParse (s, out intValue))
+                                       if (Int32.TryParse (s, NumberStyles.Integer, CultureInfo.InvariantCulture, out intValue))
                                                result = intValue;
-                                       else if (Int64.TryParse (s, out longValue))
+                                       else if (Int64.TryParse (s, NumberStyles.Integer, CultureInfo.InvariantCulture, out longValue))
                                                result = longValue;
-                                       else if (Decimal.TryParse (s, out decimalValue))
+                                       else if (Decimal.TryParse (s, NumberStyles.Integer, CultureInfo.InvariantCulture, out decimalValue))
                                                result = decimalValue;
-                                       else if (Double.TryParse (s, out doubleValue))
+                                       else if (Double.TryParse (s, NumberStyles.Integer, CultureInfo.InvariantCulture, out doubleValue))
                                                result = doubleValue;
                                        else
                                                converted = false;
                                        break;
 
                                case JsonType.FLOAT:
-                                       if (Decimal.TryParse (s, out decimalValue))
+                                       if (Decimal.TryParse (s, NumberStyles.Float, CultureInfo.InvariantCulture, out decimalValue))
                                                result = decimalValue;
-                                       else if (Double.TryParse (s, out doubleValue))
+                                       else if (Double.TryParse (s, NumberStyles.Float, CultureInfo.InvariantCulture, out doubleValue))
                                                result = doubleValue;
                                        else
                                                converted = false;
index 8dc9e38c43b75b78c8be7d286bc3bf4736c51827..61e4b502d66fa576ee93829bd322d9ef8bfb2f30 100644 (file)
@@ -1439,5 +1439,43 @@ namespace MonoTests.System.Web.Script.Serialization
                        Assert.AreEqual (1337.0, obj.d);
                        Assert.AreEqual (null, obj.o);
                }
+
+               [Test]
+               public void DeserializeInCultureWithCommaSeparator ()
+               {
+                       var origCulture = Thread.CurrentThread.CurrentCulture;
+
+                       try {
+                               Thread.CurrentThread.CurrentCulture = new CultureInfo ("en-US");
+                               CommaSeparatorTest ();
+
+                               Thread.CurrentThread.CurrentCulture = new CultureInfo ("fi-FI");
+                               CommaSeparatorTest ();
+                       } finally {
+                               Thread.CurrentThread.CurrentCulture = origCulture;
+                       }
+               }
+
+               public class DoubleTest
+               {
+                       public double[] value { get; set; }
+               }
+
+               void CommaSeparatorTest()
+               {
+                       JavaScriptSerializer serializer = new JavaScriptSerializer ();
+
+                       DoubleTest array = new DoubleTest ();
+                       array.value = new[] { 123.345, 0.69 };
+
+                       string arrayJson = serializer.Serialize (array);
+                       Console.WriteLine (arrayJson);
+
+                       // This throwed incorrectly a "System.ArgumentException: Invalid JSON primitive: 123.345" with a CurrentThread.CultureInfo that has a comma as the number separator.
+                       DoubleTest obj = serializer.Deserialize<DoubleTest> (arrayJson);
+
+                       Assert.AreEqual (123.345, obj.value[0], "#1");
+                       Assert.AreEqual (0.69, obj.value[1], "#2");
+               }
        }
 }
diff --git a/mcs/class/System.Web.Mobile/Assembly/AssemblyInfo.cs b/mcs/class/System.Web.Mobile/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..7870e25
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Web.Mobile.dll")]
+[assembly: AssemblyDescription ("System.Web.Mobile.dll")]
+[assembly: AssemblyDefaultAlias ("System.Web.Mobile.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Web.Mobile/Makefile b/mcs/class/System.Web.Mobile/Makefile
new file mode 100644 (file)
index 0000000..c2c977e
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Web.Mobile
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Web.Mobile.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../msfinal.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Web.Mobile/System.Web.Mobile.dll.sources b/mcs/class/System.Web.Mobile/System.Web.Mobile.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
diff --git a/mcs/class/System.Web.RegularExpressions/Assembly/AssemblyInfo.cs b/mcs/class/System.Web.RegularExpressions/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..ebd7f45
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Web.RegularExpressions.dll")]
+[assembly: AssemblyDescription ("System.Web.RegularExpressions.dll")]
+[assembly: AssemblyDefaultAlias ("System.Web.RegularExpressions.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Web.RegularExpressions/Makefile b/mcs/class/System.Web.RegularExpressions/Makefile
new file mode 100644 (file)
index 0000000..a16648c
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Web.RegularExpressions
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Web.RegularExpressions.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../msfinal.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Web.RegularExpressions/System.Web.RegularExpressions.dll.sources b/mcs/class/System.Web.RegularExpressions/System.Web.RegularExpressions.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
index c189f7963eb63425694f478679cdad6841ffab3d..0e8dd48092a02ed4dec8aa97c7c34f192ae50502 100644 (file)
@@ -7,9 +7,6 @@ ifdef MOBILE_PROFILE
 LIB_REFS = System System.Xml
 LIB_MCS_FLAGS = \
        -nowarn:649 -nowarn:169                 \
-       -r:$(corlib)                            \
-       -r:System.dll                           \
-       -r:System.Xml.dll                       \
        -resource:System.Web.Services.Description/wsdl-1.1.xsd,wsdl-1.1.xsd \
        -resource:System.Web.Services.Description/wsdl-1.1-soap.xsd,wsdl-1.1-soap.xsd \
        -resource:System.Web.Services.Description/web-reference.xsd,web-reference.xsd
@@ -18,19 +15,15 @@ LIB_REFS = System System.EnterpriseServices System.Xml System.Data
 LIB_MCS_FLAGS = -nowarn:168,169,219,414,612,649 -d:MONO_BROKEN_CONFIGURATION_DLL
 
 ifndef NO_SYSTEM_WEB_DEPENDENCY
-LIB_REFS += System.Web
-plainweb_dir = $(the_libdir_base)plainweb
-plainweb = $(plainweb_dir)/System.Web.dll
-system_web_services_deps = $(plainweb)
-LOCAL_MCS_FLAGS += -lib:$(plainweb_dir)
+plainweb = $(the_libdir_base)plainweb/System.Web.dll
+system_web_deps = $(plainweb)
+LIB_REFS += plainweb/System.Web
 endif
 
 ifndef NO_SYSTEM_DESIGN_DEPENDENCY
-LIB_REFS += System.Design
-plaindesign_dir = $(the_libdir_base)plaindesign
-plaindesign = $(plaindesign_dir)/System.Design.dll
+plaindesign = $(the_libdir_base)plaindesign/System.Design.dll
 system_design_deps = $(plaindesign)
-LOCAL_MCS_FLAGS += -lib:$(plaindesign_dir)
+LIB_REFS += plaindesign/System.Design
 endif
 
 ifndef NO_SYSTEM_DIRECTORY_SERVICES_DEPENDENCY
@@ -63,7 +56,7 @@ EXTRA_DISTFILES = \
 
 include ../../build/library.make
 
-$(the_libdir_base)$(LIBRARY): $(system_web_services_deps) $(system_design_deps)
+$(the_libdir_base)$(LIBRARY): $(system_web_deps) $(system_design_deps)
 
 $(plainweb):
        (cd ../System.Web; $(MAKE) $@)
index 72f14d105779d04a3118b84c4d456bc0fce77c8c..7659f4e0498920b4845956e3bc2c9c5263374e6a 100644 (file)
@@ -233,33 +233,33 @@ NUNIT_APP_CODE_FILES = $(TEST_APP_CODE_FILES)
 NUNIT_APP_GLOBALRESOURCES_FILES = $(TEST_APP_GLOBALRESOURCES_FILES)
 
 OTHER_RES += $(RESOURCE_FILES_2)
-OTHER_LIB_MCS_FLAGS = -d:INSIDE_SYSTEM_WEB -nowarn:618 -r:System.Configuration.dll -r:Mono.Data.Sqlite.dll
+OTHER_LIB_MCS_FLAGS = -d:INSIDE_SYSTEM_WEB -nowarn:618
 
 ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
-OTHER_LIB_MCS_FLAGS += -r:System.Web.ApplicationServices.dll
 OTHER_RES += $(RESOURCE_FILES_4)
 endif
 
 TXT_RESOURCE_STRINGS = ../../../external/referencesource/System.Web/System.Web.txt
 
-LIB_REFS = System System.Core System.Drawing System.Data System.Xml System.EnterpriseServices System.Runtime.Serialization.Formatters.Soap System.ComponentModel.DataAnnotations
+LIB_REFS = System System.Core System.Drawing System.Data System.Xml System.EnterpriseServices System.Runtime.Serialization.Formatters.Soap \
+       System.ComponentModel.DataAnnotations System.Web.ApplicationServices System.Configuration Mono.Data.Sqlite
 LIB_MCS_FLAGS = \
        -unsafe \
        -nowarn:612,618 \
-       -r:$(corlib)                    \
        $(OTHER_LIB_MCS_FLAGS) \
        $(RESX_RES:%=/resource:%) \
        $(OTHER_RES:%=/resource:%)
 
 ifneq (plainweb/,$(intermediate))
-LIB_REFS += System.Web.Services System.Design
-LIB_MCS_FLAGS += -define:WEBSERVICES_DEP -lib:$(the_libdir_base)plaindesign
+LIB_REFS += System.Web.Services plaindesign/System.Design
+LIB_MCS_FLAGS += -define:WEBSERVICES_DEP
 
 all-local: System.Web/UplevelHelper.cs resources/TranslationResources.resources 
 
 endif
 
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -doc:$(test_lib:.dll=.xml) -nowarn:219,169,1591 -r:SystemWebTestShim.dll \
+TEST_LIB_REFS = SystemWebTestShim
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -doc:$(test_lib:.dll=.xml) -nowarn:219,169,1591 \
        $(NUNIT_RESOURCE_FILES:%=/resource:%) \
        $(foreach file,$(NUNIT_APP_CODE_FILES),$(shell echo $(file) | sed -e 's;\(.*\)/\(.*\);/resource:\1/\2,App_Code/\2 ;g')) \
        $(foreach file,$(NUNIT_APP_GLOBALRESOURCES_FILES),$(shell echo $(file) | sed -e 's;\(.*\)/\(.*\);/resource:\1/\2,App_GlobalResources/\2 ;g'))
@@ -322,11 +322,11 @@ endif
 
 CLASSLIB_DIR = $(topdir)/class/lib/$(PROFILE)
 
-STANDALONE_RUNNER_SUPPORT_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -d:STANDALONE_TEST -debug:full -r:System.Web.dll -r:nunit.framework.dll
+STANDALONE_RUNNER_SUPPORT_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -d:STANDALONE_TEST -r:$(topdir)/class/lib/$(PROFILE)/System.Web.dll -r:$(topdir)/class/lib/$(PROFILE)/nunit.framework.dll
 STANDALONE_RUNNER_SUPPORT_ASSEMBLY = $(CLASSLIB_DIR)/standalone-runner-support.dll
 STANDALONE_RUNNER_SUPPORT_MAKEFRAG = $(depsdir)/$(PROFILE)_standalone-runner-support.dll.makefrag
 
-STANDALONE_TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -debug:full -r:$(STANDALONE_RUNNER_SUPPORT_ASSEMBLY) -r:System.Web.dll -r:nunit.framework.dll
+STANDALONE_TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) $(PROFILE_MCS_FLAGS) -r:$(STANDALONE_RUNNER_SUPPORT_ASSEMBLY) -r:$(topdir)/class/lib/$(PROFILE)/System.Web.dll -r:$(topdir)/class/lib/$(PROFILE)/nunit.framework.dll
 STANDALONE_TEST_ASSEMBLY = System.Web_standalone_test_$(PROFILE).dll
 STANDALONE_TEST_MAKEFRAG = $(depsdir)/$(STANDALONE_TEST_ASSEMBLY).makefrag
 
index a8cd2f842cb2d887242b5e8292085c3e6410e5e2..7f59b52e22b47f90653406803db3f8ef8acc6c08 100644 (file)
@@ -79,7 +79,9 @@ namespace System.Web.Handlers
                                        if (!hashAlg.CanReuseTransform) {
                                                canReuseHashAlg = false;
                                                hashAlg = null;
+                                               return null;
                                        }
+                                       hashAlg.Key = MachineKeySectionUtils.GetValidationKey (mks);
                                }
 
                                if (hashAlg != null)
index bfe9f95caa27775f0c959b4c0ca17c8ae708845a..9cbb4159d004d5bf1c20d5f539f159e050336666 100644 (file)
@@ -10,9 +10,9 @@ STANDALONE_RUNNER_SOURCES = \
        ../../../Mono.Options/Mono.Options/Options.cs \
 
 STANDALONE_RUNNER_REFERENCES = \
-       -lib:$(CLASSLIB_DIR) \
        -r:$(STANDALONE_RUNNER_SUPPORT_ASSEMBLY) \
-       -r:System.Web.dll
+       -r:$(CLASSLIB_DIR)/System.Web.dll \
+       -r:$(CLASSLIB_DIR)/System.dll
 
 CACHE_PQ_TEST_GENERATOR_SOURCES = \
        CachePQTestGenerator/CacheItemComparer.cs \
@@ -27,7 +27,6 @@ CACHE_PQ_TEST_GENERATOR_SOURCES = \
        ../System.Web.Caching/CacheItemPriorityQueueTestSupport.cs
 
 CACHE_PQ_TEST_GENERATOR_REFERENCES = \
-       -lib:$(CLASSLIB_DIR) \
        -pkg:dotnet
 
 CACHE_PQ_TEST_SEQUENCES = $(wildcard ./CachePQTestGenerator/Sequences/*.seq)
@@ -36,13 +35,13 @@ CACHE_PQ_TEST_PACKED_SEQUENCES = $(wildcard ./CachePQTestGenerator/Sequences/*.s
 all-local: HtmlWriter.dll standalone-runner.exe cache-pq-test-generator.exe
 
 HtmlWriter.dll: HtmlWriter.cs
-       $(MCS) -t:library -r:System.Web.dll $<
+       $(CSCOMPILE) -t:library -r:System.Web.dll $<
 
 standalone-runner.exe: deps $(STANDALONE_RUNNER_SOURCES)
-       $(MCS) -debug:full $(STANDALONE_RUNNER_REFERENCES) -out:$@ $(STANDALONE_RUNNER_SOURCES)
+       $(CSCOMPILE) $(STANDALONE_RUNNER_REFERENCES) -out:$@ $(STANDALONE_RUNNER_SOURCES)
 
 cache-pq-test-generator.exe: $(CACHE_PQ_TEST_GENERATOR_SOURCES)
-       $(MCS) -debug:full -d:DEBUG $(CACHE_PQ_TEST_GENERATOR_REFERENCES) -out:$@ $(CACHE_PQ_TEST_GENERATOR_SOURCES)
+       $(CSCOMPILE) -d:DEBUG $(CACHE_PQ_TEST_GENERATOR_REFERENCES) -out:$@ $(CACHE_PQ_TEST_GENERATOR_SOURCES)
 
 generate-cache-pq-tests: cache-pq-test-generator.exe 
        for f in $(patsubst %.seq.gz,%.seq,$(CACHE_PQ_TEST_PACKED_SEQUENCES)); do \
index 3d8113656cf5f9dd2acce3436c67bd6a1e9c3e27..06eacbcbcf7cd073d64de672105b60d866fa266a 100644 (file)
@@ -5,7 +5,6 @@ LIBRARY = System.Windows.Forms.dll
 
 LIB_REFS = System System.Xml System.Drawing Accessibility System.Data Mono.Posix Mono.WebBrowser System.Configuration System.Runtime.Serialization.Formatters.Soap
 LIB_MCS_FLAGS = /unsafe \
-       /r:$(corlib) \
        @System.Windows.Forms.dll.resources \
        -nowarn:618,612,809
 
@@ -100,13 +99,15 @@ EXTRA_DISTFILES = \
        $(IMAGES_RESOURCES) \
        $(TEST_DISTFILES)
 
-TEST_MCS_FLAGS = /r:System.Data.dll /r:System.Drawing.dll /r:Accessibility.dll -r:System.dll -r:System.Xml.dll -r:System.Runtime.Serialization.Formatters.Soap\
+TEST_LIB_REFS = System.Data System.Drawing Accessibility System System.Xml System.Runtime.Serialization.Formatters.Soap
+TEST_MCS_FLAGS = \
        -resource:Test/resources/a.cur,a.cur \
        -resource:Test/resources/32x32.ico,32x32.ico \
        -nowarn:618,612
 
 DummyAssembly.dll:
-       $(CSCOMPILE) /target:library /out:$@ Test/DummyAssembly/AnotherSerializable.cs Test/DummyAssembly/Convertable.cs Test/DummyAssembly/Properties/AssemblyInfo.cs
+       $(CSCOMPILE) /target:library /out:$@ Test/DummyAssembly/AnotherSerializable.cs Test/DummyAssembly/Convertable.cs Test/DummyAssembly/Properties/AssemblyInfo.cs \
+       -r:$(topdir)/class/lib/$(PROFILE)/System.dll
 
 test-local: DummyAssembly.dll
 
diff --git a/mcs/class/System.Workflow.Activities/Assembly/AssemblyInfo.cs b/mcs/class/System.Workflow.Activities/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..5a1b6a1
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Workflow.Activities.dll")]
+[assembly: AssemblyDescription ("System.Workflow.Activities.dll")]
+[assembly: AssemblyDefaultAlias ("System.Workflow.Activities.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Workflow.Activities/Makefile b/mcs/class/System.Workflow.Activities/Makefile
new file mode 100644 (file)
index 0000000..bda9e38
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Workflow.Activities
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Workflow.Activities.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../winfx.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Workflow.Activities/System.Workflow.Activities.dll.sources b/mcs/class/System.Workflow.Activities/System.Workflow.Activities.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
diff --git a/mcs/class/System.Workflow.ComponentModel/Assembly/AssemblyInfo.cs b/mcs/class/System.Workflow.ComponentModel/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..6526e77
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Workflow.ComponentModel.dll")]
+[assembly: AssemblyDescription ("System.Workflow.ComponentModel.dll")]
+[assembly: AssemblyDefaultAlias ("System.Workflow.ComponentModel.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Workflow.ComponentModel/Makefile b/mcs/class/System.Workflow.ComponentModel/Makefile
new file mode 100644 (file)
index 0000000..6b988f2
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Workflow.ComponentModel
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Workflow.ComponentModel.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../winfx.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Workflow.ComponentModel/System.Workflow.ComponentModel.dll.sources b/mcs/class/System.Workflow.ComponentModel/System.Workflow.ComponentModel.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
diff --git a/mcs/class/System.Workflow.Runtime/Assembly/AssemblyInfo.cs b/mcs/class/System.Workflow.Runtime/Assembly/AssemblyInfo.cs
new file mode 100644 (file)
index 0000000..d967638
--- /dev/null
@@ -0,0 +1,53 @@
+//
+// AssemblyInfo.cs
+//
+// Authors:
+//     Marek Safar (marek.safar@gmail.com)
+//
+// Copyright 2016 Xamarin Inc (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Reflection;
+using System.Resources;
+using System.Security;
+using System.Security.Permissions;
+using System.Diagnostics;
+using System.Runtime.CompilerServices;
+using System.Runtime.InteropServices;
+
+// General Information about the assembly
+
+[assembly: AssemblyTitle ("System.Workflow.Runtime.dll")]
+[assembly: AssemblyDescription ("System.Workflow.Runtime.dll")]
+[assembly: AssemblyDefaultAlias ("System.Workflow.Runtime.dll")]
+
+[assembly: AssemblyCompany (Consts.MonoCompany)]
+[assembly: AssemblyProduct (Consts.MonoProduct)]
+[assembly: AssemblyCopyright (Consts.MonoCopyright)]
+[assembly: AssemblyVersion (Consts.FxVersion)]
+[assembly: SatelliteContractVersion (Consts.FxVersion)]
+[assembly: AssemblyInformationalVersion (Consts.FxFileVersion)]
+[assembly: AssemblyFileVersion (Consts.FxFileVersion)]
+
+[assembly: CLSCompliant (true)]
+
diff --git a/mcs/class/System.Workflow.Runtime/Makefile b/mcs/class/System.Workflow.Runtime/Makefile
new file mode 100644 (file)
index 0000000..d8c4f7c
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = class/System.Workflow.Runtime
+SUBDIRS = 
+include ../../build/rules.make
+
+LIBRARY = System.Workflow.Runtime.dll
+
+LIB_REFS =
+LIB_MCS_FLAGS = -delaysign -keyfile:../winfx.pub
+
+include ../../build/library.make
diff --git a/mcs/class/System.Workflow.Runtime/System.Workflow.Runtime.dll.sources b/mcs/class/System.Workflow.Runtime/System.Workflow.Runtime.dll.sources
new file mode 100644 (file)
index 0000000..e49bef5
--- /dev/null
@@ -0,0 +1,2 @@
+../../build/common/Consts.cs
+Assembly/AssemblyInfo.cs
index 183612a105348969632ad26a81b0835b28379a36..e66bd2e4635074301139ad12b82b242026bc4fda 100644 (file)
@@ -17,23 +17,24 @@ TXT_RESOURCE_STRINGS = \
        ../../../external/referencesource/System.Xml/System.Xml.txt \
        ../../../external/referencesource/System.Data.SqlXml/System.Xml.Utils.txt
 
-LIB_REFS = System
-LIB_MCS_FLAGS = -r:$(corlib)  -nowarn:219,414,649,1717 -unsafe -d:ASYNC
+LIB_MCS_FLAGS = -nowarn:219,414,649,1717 -unsafe -d:ASYNC
 
 ifeq (2.1, $(FRAMEWORK_VERSION))
 LIB_MCS_FLAGS += -d:AGCLR -d:NET_2_1_HACK -d:DISABLE_XSLT_COMPILER -d:DISABLE_XSLT_SCRIPT,MONO_HYBRID_SYSTEM_XML -d:DISABLE_CAS_USE
 endif
-TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169 -r:System.Data.dll -r:System.Core.dll
 
-ifndef MOBILE_PROFILE
-FINAL_MCS_FLAGS = -r:System.Configuration.dll -d:CONFIGURATION_DEP
-endif
+TEST_LIB_REFS = System.Data System.Core
+TEST_MCS_FLAGS = $(LIB_MCS_FLAGS) -nowarn:0618 -nowarn:219 -nowarn:169
 
 ifneq (bare/,$(intermediate))
-LIB_MCS_FLAGS += $(FINAL_MCS_FLAGS)
+LIB_REFS += secxml/System 
+ifndef MOBILE_PROFILE
+LIB_REFS += System.Configuration
+LIB_MCS_FLAGS += -d:CONFIGURATION_DEP
+endif
+else
+LIB_REFS += $(intermediate)System
 endif
-
-LOCAL_MCS_FLAGS += -lib:$(bare_libdir)
 
 nist_dom_files = \
        ITest.cs readme.txt util.cs \
index a7651da891f7900adbb0b0cead4fa0ad03b94ce3..69456085a2bda90e18facc43bc4dcfcdffedf776 100644 (file)
@@ -83,3 +83,5 @@ using System.Runtime.InteropServices;
        [assembly: InternalsVisibleTo ("Mono.Security.Providers.NewTls, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
        [assembly: InternalsVisibleTo ("Mono.Security.Providers.DotNet, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
        [assembly: InternalsVisibleTo ("Mono.Security, PublicKey=002400000480000094000000060200000024000052534131000400000100010079159977d2d03a8e6bea7a2e74e8d1afcc93e8851974952bb480a12c9134474d04062447c37e0e68c080536fcf3c3fbe2ff9c979ce998475e506e8ce82dd5b0f350dc10e93bf2eeecf874b24770c5081dbea7447fddafa277b22de47d6ffea449674a4f9fccf84d15069089380284dbdd35f46cdff12a1bd78e4ef0065d016df")]
+
+       [assembly: InternalsVisibleTo ("Xamarin.BoringTls, PublicKey=002400000480000094000000060200000024000052534131000400001100000099dd12eda85767ae6f06023ee28e711c7e5a212462095c83868c29db75eddf6d8e296e03824c14fedd5f55553fed0b6173be3cc985a4b7f9fb7c83ccff8ba3938563b3d1f45a81122f12a1bcb73edcaad61a8456c7595a6da5184b4dd9d10f011b949ef1391fccfeab1ba62aa51c267ef8bd57ef1b6ba5a4c515d0badb81a78f")]
diff --git a/mcs/class/System/Assembly/AssemblyInfoEx.cs b/mcs/class/System/Assembly/AssemblyInfoEx.cs
new file mode 100644 (file)
index 0000000..22e5bca
--- /dev/null
@@ -0,0 +1,7 @@
+using System.Runtime.CompilerServices;
+
+[assembly: InternalsVisibleTo ("monotouch, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
+[assembly: InternalsVisibleTo ("Xamarin.iOS, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
+[assembly: InternalsVisibleTo ("Xamarin.Mac, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
+[assembly: InternalsVisibleTo ("Xamarin.WatchOS, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
+[assembly: InternalsVisibleTo ("Xamarin.TVOS, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
index 25031265acc6825dabdb97cc1350dabdce1a4215..3adbdbf3917b8b3ab8e8be7411a7b8b0dd40c82c 100644 (file)
@@ -19,7 +19,9 @@ TEST_RESOURCES = \
        Test/System/test-uri-props-manual.txt \
        Test/System/test-uri-relative-props.txt
 
-TEST_MCS_FLAGS = -r:System.Drawing.dll -r:Mono.Security.dll -r:System.Data.dll -r:System.Xml.dll -r:System.Core.dll -nowarn:618,672,219,67,169,612 \
+TEST_LIB_REFS = System.Drawing Mono.Security System.Data System.Xml System.Core System.Configuration
+
+TEST_MCS_FLAGS = -nowarn:618,672,219,67,169,612 \
        $(foreach f, $(TEST_RESOURCES), -resource:$(f),$(notdir $(f)))
 
 REFERENCE_SOURCES_FLAGS = -d:FEATURE_PAL,SYSTEM_NAMESPACE,MONO,PLATFORM_UNIX
@@ -29,7 +31,6 @@ TEST_MCS_FLAGS += -d:MONO_FEATURE_PROCESS_START
 endif
 
 LIB_MCS_FLAGS = -nowarn:618 -d:CONFIGURATION_2_0 $(REFERENCE_SOURCES_FLAGS) -unsafe $(RESOURCE_FILES:%=-resource:%)
-TEST_MCS_FLAGS += -r:System.Configuration.dll
 
 ifndef NO_THREAD_ABORT
 REFERENCE_SOURCES_FLAGS += -d:MONO_FEATURE_THREAD_ABORT
@@ -49,17 +50,16 @@ TXT_RESOURCE_STRINGS = ../../../external/referencesource/System/System.txt
 ifdef MOBILE_PROFILE
 LIB_MCS_FLAGS += -d:INSIDE_SYSTEM -d:SECURITY_DEP
 else
-EXTERN_ALIAS_FLAGS = -d:MONO_SECURITY_ALIAS -d:MONO_X509_ALIAS
-FINAL_MCS_FLAGS = -r:System.Configuration.dll -d:CONFIGURATION_DEP
+EXTERN_ALIAS_FLAGS = -d:MONO_SECURITY_ALIAS
 endif
 
 #
 # Flags used to build the secxml version of System.
 #
 ifeq (secxml/, $(intermediate))
-LOCAL_MCS_FLAGS = -lib:$(bare_libdir) 
-LIB_REFS += System.Xml MonoSecurity=Mono.Security
-LIB_MCS_FLAGS += -d:SECURITY_DEP -d:XML_DEP -r:PrebuiltSystem=$(bare_libdir)/System.dll $(EXTERN_ALIAS_FLAGS)
+LOCAL_MCS_FLAGS =
+LIB_REFS += bare/System.Xml MonoSecurity=Mono.Security
+LIB_MCS_FLAGS += -d:SECURITY_DEP -d:XML_DEP $(EXTERN_ALIAS_FLAGS)
 endif
 
 #
@@ -67,7 +67,13 @@ endif
 #
 ifndef intermediate
 LIB_REFS += System.Xml MonoSecurity=Mono.Security
-LIB_MCS_FLAGS += -d:SECURITY_DEP -d:XML_DEP -r:PrebuiltSystem=$(secxml_libdir)/System.dll $(EXTERN_ALIAS_FLAGS) $(FINAL_MCS_FLAGS)
+LIB_MCS_FLAGS += -d:SECURITY_DEP -d:XML_DEP $(EXTERN_ALIAS_FLAGS)
+
+ifndef MOBILE_PROFILE
+LIB_REFS += System.Configuration
+LIB_MCS_FLAGS += -d:CONFIGURATION_DEP
+endif
+
 endif
 
 EXTRA_DISTFILES = \
index 675d20f06d460620376a2361fa9ffbf8b999bd58..a4de75e853a54719fc8293f8852e83e2e32092be 100644 (file)
@@ -366,6 +366,8 @@ namespace Mono.CSharp
                                }
                        }
 
+                       args.Append ("/noconfig ");
+
                        args.Append (" -- ");
                        foreach (string source in fileNames)
                                args.AppendFormat("\"{0}\" ",source);
index 6ae2b9f3ca8d7d2ef1cc06fc06d4ab80a73f3fda..e79c167c01ecec86236184b3a72cbe33d752d8a7 100644 (file)
@@ -26,9 +26,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -38,13 +35,6 @@ using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-using XX509Chain = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509Chain;
-#else
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-using XX509Chain = System.Security.Cryptography.X509Certificates.X509Chain;
-#endif
 
 using System;
 using System.IO;
@@ -64,7 +54,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (h, c, ch, e) => callback (h, c, (X509Chain)(object)ch, (SslPolicyErrors)e);
+                       return (h, c, ch, e) => callback (h, c, ch, (SslPolicyErrors)e);
                }
 
                internal static MSI.MonoLocalCertificateSelectionCallback PublicToMono (LocalCertificateSelectionCallback callback)
@@ -72,7 +62,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (t, lc, rc, ai) => callback (null, t, (XX509CertificateCollection)(object)lc, rc, ai);
+                       return (t, lc, rc, ai) => callback (null, t, lc, rc, ai);
                }
 
                internal static MSI.MonoRemoteCertificateValidationCallback InternalToMono (RemoteCertValidationCallback callback)
@@ -80,7 +70,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (h, c, ch, e) => callback (h, c, (X509Chain)(object)ch, (SslPolicyErrors)e);
+                       return (h, c, ch, e) => callback (h, c, ch, (SslPolicyErrors)e);
                }
 
                internal static RemoteCertificateValidationCallback InternalToPublic (string hostname, RemoteCertValidationCallback callback)
@@ -96,7 +86,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (t, lc, rc, ai) => callback (t, (XX509CertificateCollection)(object)lc, rc, ai);
+                       return (t, lc, rc, ai) => callback (t, lc, rc, ai);
                }
 
                internal static RemoteCertificateValidationCallback MonoToPublic (MSI.MonoRemoteCertificateValidationCallback callback)
@@ -104,7 +94,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (t, c, ch, e) => callback (null, c, (XX509Chain)(object)ch, (MSI.MonoSslPolicyErrors)e);
+                       return (t, c, ch, e) => callback (null, c, ch, (MSI.MonoSslPolicyErrors)e);
                }
 
                internal static LocalCertificateSelectionCallback MonoToPublic (MSI.MonoLocalCertificateSelectionCallback callback)
@@ -112,7 +102,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (s, t, lc, rc, ai) => callback (t, (XX509CertificateCollection)(object)lc, rc, ai);
+                       return (s, t, lc, rc, ai) => callback (t, lc, rc, ai);
                }
 
                internal static RemoteCertValidationCallback MonoToInternal (MSI.MonoRemoteCertificateValidationCallback callback)
@@ -120,7 +110,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (h, c, ch, e) => callback (h, c, (XX509Chain)(object)ch, (MSI.MonoSslPolicyErrors)e);
+                       return (h, c, ch, e) => callback (h, c, ch, (MSI.MonoSslPolicyErrors)e);
                }
 
                internal static LocalCertSelectionCallback MonoToInternal (MSI.MonoLocalCertificateSelectionCallback callback)
@@ -128,7 +118,7 @@ namespace Mono.Net.Security.Private
                        if (callback == null)
                                return null;
 
-                       return (t, lc, rc, ai) => callback (t, (XX509CertificateCollection)(object)lc, rc, ai);
+                       return (t, lc, rc, ai) => callback (t, lc, rc, ai);
                }
 
        }
index 63a781dbdf5a7d37628af8efb85473e6692d486e..5d2812d2738e4c51c72af55564a3e3c95356e0c4 100644 (file)
@@ -34,9 +34,6 @@
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MonoSecurity::Mono.Security.Interface;
@@ -47,13 +44,8 @@ using Mono.Security.Interface;
 using MSX = Mono.Security.X509;
 using Mono.Security.X509.Extensions;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-using XX509Chain = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509Chain;
-#else
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
 using XX509Chain = System.Security.Cryptography.X509Certificates.X509Chain;
-#endif
 
 using System;
 using System.Net;
@@ -74,7 +66,7 @@ namespace Mono.Net.Security
 {
        internal delegate bool ServerCertValidationCallbackWrapper (ServerCertValidationCallback callback, X509Certificate certificate, X509Chain chain, MonoSslPolicyErrors sslPolicyErrors);
 
-       internal class ChainValidationHelper : ICertificateValidator
+       internal class ChainValidationHelper : ICertificateValidator2
        {
                readonly object sender;
                readonly MonoTlsSettings settings;
@@ -228,7 +220,7 @@ namespace Mono.Net.Security
                        var certs = new XX509CertificateCollection ();
                        certs.Add (new X509Certificate2 (certificate.GetRawCertData ()));
 
-                       var result = ValidateChain (string.Empty, true, certs, (SslPolicyErrors)errors);
+                       var result = ValidateChain (string.Empty, true, certificate, null, certs, (SslPolicyErrors)errors);
                        if (result == null)
                                return false;
 
@@ -238,7 +230,27 @@ namespace Mono.Net.Security
                public ValidationResult ValidateCertificate (string host, bool serverMode, XX509CertificateCollection certs)
                {
                        try {
-                               var result = ValidateChain (host, serverMode, certs, 0);
+                               X509Certificate leaf;
+                               if (certs != null && certs.Count != 0)
+                                       leaf = certs [0];
+                               else
+                                       leaf = null;
+                               var result = ValidateChain (host, serverMode, leaf, null, certs, 0);
+                               if (tlsStream != null)
+                                       tlsStream.CertificateValidationFailed = result == null || !result.Trusted || result.UserDenied;
+                               return result;
+                       } catch {
+                               if (tlsStream != null)
+                                       tlsStream.CertificateValidationFailed = true;
+                               throw;
+                       }
+               }
+
+               public ValidationResult ValidateCertificate (string host, bool serverMode, X509Certificate leaf, XX509Chain xchain)
+               {
+                       try {
+                               var chain = xchain;
+                               var result = ValidateChain (host, serverMode, leaf, chain, null, 0);
                                if (tlsStream != null)
                                        tlsStream.CertificateValidationFailed = result == null || !result.Trusted || result.UserDenied;
                                return result;
@@ -249,7 +261,28 @@ namespace Mono.Net.Security
                        }
                }
 
-               ValidationResult ValidateChain (string host, bool server, XX509CertificateCollection certs, SslPolicyErrors errors)
+               ValidationResult ValidateChain (string host, bool server, X509Certificate leaf,
+                                               X509Chain chain, XX509CertificateCollection certs,
+                                               SslPolicyErrors errors)
+               {
+                       var oldChain = chain;
+                       var ownsChain = chain == null;
+                       try {
+                               var result = ValidateChain (host, server, leaf, ref chain, certs, errors);
+                               if (chain != oldChain)
+                                       ownsChain = true;
+
+                               return result;
+                       } finally {
+                               // If ValidateChain() changed the chain, then we need to free it.
+                               if (ownsChain && chain != null)
+                                       chain.Dispose ();
+                       }
+               }
+
+               ValidationResult ValidateChain (string host, bool server, X509Certificate leaf,
+                                               ref X509Chain chain, XX509CertificateCollection certs,
+                                               SslPolicyErrors errors)
                {
                        // user_denied is true if the user callback is called and returns false
                        bool user_denied = false;
@@ -257,12 +290,6 @@ namespace Mono.Net.Security
 
                        var hasCallback = certValidationCallback != null || callbackWrapper != null;
 
-                       X509Certificate leaf;
-                       if (certs == null || certs.Count == 0)
-                               leaf = null;
-                       else
-                               leaf = certs [0];
-
                        if (tlsStream != null)
                                request.ServicePoint.UpdateServerCertificate (leaf);
 
@@ -281,7 +308,6 @@ namespace Mono.Net.Security
                        ICertificatePolicy policy = ServicePointManager.GetLegacyCertificatePolicy ();
 
                        int status11 = 0; // Error code passed to the obsolete ICertificatePolicy callback
-                       X509Chain chain = null;
 
                        bool wantsChain = SystemCertificateValidator.NeedsChain (settings);
                        if (!wantsChain && hasCallback) {
@@ -289,15 +315,15 @@ namespace Mono.Net.Security
                                        wantsChain = true;
                        }
 
-                       if (wantsChain)
-                               chain = SystemCertificateValidator.CreateX509Chain (certs);
-
                        bool providerValidated = false;
                        if (provider != null && provider.HasCustomSystemCertificateValidator) {
                                var xerrors = (MonoSslPolicyErrors)errors;
-                               var xchain = (XX509Chain)(object)chain;
-                               providerValidated = provider.InvokeSystemCertificateValidator (this, host, server, certs, xchain, out result, ref xerrors, ref status11);
+                               var xchain = chain;
+                               providerValidated = provider.InvokeSystemCertificateValidator (this, host, server, certs, wantsChain, ref xchain, out result, ref xerrors, ref status11);
+                               chain = xchain;
                                errors = (SslPolicyErrors)xerrors;
+                       } else if (wantsChain) {
+                               chain = SystemCertificateValidator.CreateX509Chain (certs);
                        }
 
                        if (!providerValidated)
@@ -329,7 +355,7 @@ namespace Mono.Net.Security
 
                public bool InvokeSystemValidator (string targetHost, bool serverMode, XX509CertificateCollection certificates, XX509Chain xchain, ref MonoSslPolicyErrors xerrors, ref int status11)
                {
-                       X509Chain chain = (X509Chain)(object)xchain;
+                       X509Chain chain = xchain;
                        var errors = (SslPolicyErrors)xerrors;
                        var result = SystemCertificateValidator.Evaluate (settings, targetHost, certificates, chain, ref errors, ref status11);
                        xerrors = (MonoSslPolicyErrors)errors;
index 50193cc2ec19c6461764e14b83677de04c00ad1f..69daf52111386fec045981afd515d03864d37d0c 100644 (file)
 // THE SOFTWARE.
 
 #if SECURITY_DEP
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
 
-#if MONO_X509_ALIAS
-using X509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 #if MONO_SECURITY_ALIAS
 using MSI = MonoSecurity::Mono.Security.Interface;
 #else
index 478ed585b59c2956d8c6d0aa0fd2c115cb3405f0..50b4cd9c8c460de1aee7dd57382fe1eb0b204326 100644 (file)
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MonoSecurity::Mono.Security.Interface;
 #else
 using Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
 #endif
-#endif
 
 using System;
 using System.IO;
index ab0bc51897425ca78a33ef4061ab0ffb0d78b5ad..1a6672f6c5c36f634b575715a611d14148e86c0a 100644 (file)
@@ -34,9 +34,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -56,9 +53,6 @@ using MonoSecurityProtocolType = Mono.Security.Protocol.Tls.SecurityProtocolType
 using Mono.Security.Protocol.Tls;
 using Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using X509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using CipherAlgorithmType = System.Security.Authentication.CipherAlgorithmType;
 using HashAlgorithmType = System.Security.Authentication.HashAlgorithmType;
index d6f6e5296f454a65ac7ca9f27b6d3e001087e539..7ea40e1940172a2d422936d04fe51d0431956a69 100644 (file)
 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 // THE SOFTWARE.
 #if SECURITY_DEP
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
 
-#if MONO_X509_ALIAS
-using XHttpWebRequest = PrebuiltSystem::System.Net.HttpWebRequest;
-using XSslProtocols = PrebuiltSystem::System.Security.Authentication.SslProtocols;
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
 using XHttpWebRequest = System.Net.HttpWebRequest;
 using XSslProtocols = System.Security.Authentication.SslProtocols;
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MonoSecurity::Mono.Security.Interface;
index dfb5c8c450ac60d1be017d770bff0d34748956da..776751537bdae8df69c5134c20ade5c097c65eb5 100644 (file)
@@ -26,9 +26,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -38,27 +35,6 @@ using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-
-using XTransportContext = PrebuiltSystem::System.Net.TransportContext;
-using XAuthenticatedStream = PrebuiltSystem::System.Net.Security.AuthenticatedStream;
-
-using XCipherAlgorithmType = PrebuiltSystem::System.Security.Authentication.CipherAlgorithmType;
-using XHashAlgorithmType = PrebuiltSystem::System.Security.Authentication.HashAlgorithmType;
-using XExchangeAlgorithmType = PrebuiltSystem::System.Security.Authentication.ExchangeAlgorithmType;
-using XSslProtocols = PrebuiltSystem::System.Security.Authentication.SslProtocols;
-#else
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-
-using XTransportContext = System.Net.TransportContext;
-using XAuthenticatedStream = System.Net.Security.AuthenticatedStream;
-
-using XCipherAlgorithmType = System.Security.Authentication.CipherAlgorithmType;
-using XHashAlgorithmType = System.Security.Authentication.HashAlgorithmType;
-using XExchangeAlgorithmType = System.Security.Authentication.ExchangeAlgorithmType;
-using XSslProtocols = System.Security.Authentication.SslProtocols;
-#endif
 
 using System;
 using System.IO;
@@ -96,9 +72,9 @@ namespace Mono.Net.Security.Private
                        Impl.AuthenticateAsClient (targetHost);
                }
 
-               public void AuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public void AuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsClient (targetHost, clientCertificates, (SslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public IAsyncResult BeginAuthenticateAsClient (string targetHost, AsyncCallback asyncCallback, object asyncState)
@@ -106,9 +82,9 @@ namespace Mono.Net.Security.Private
                        return Impl.BeginAuthenticateAsClient (targetHost, asyncCallback, asyncState);
                }
 
-               public IAsyncResult BeginAuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
+               public IAsyncResult BeginAuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsClient (targetHost, clientCertificates, (SslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public void EndAuthenticateAsClient (IAsyncResult asyncResult)
@@ -121,9 +97,9 @@ namespace Mono.Net.Security.Private
                        Impl.AuthenticateAsServer (serverCertificate);
                }
 
-               public void AuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public void AuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, (SslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, AsyncCallback asyncCallback, object asyncState)
@@ -131,9 +107,9 @@ namespace Mono.Net.Security.Private
                        return Impl.BeginAuthenticateAsServer (serverCertificate, asyncCallback, asyncState);
                }
 
-               public IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
+               public IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, (SslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public void EndAuthenticateAsServer (IAsyncResult asyncResult)
@@ -146,9 +122,9 @@ namespace Mono.Net.Security.Private
                        return Impl.AuthenticateAsClientAsync (targetHost);
                }
 
-               public Task AuthenticateAsClientAsync (string targetHost, XX509CertificateCollection clientCertificates, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public Task AuthenticateAsClientAsync (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, (SslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public Task AuthenticateAsServerAsync (X509Certificate serverCertificate)
@@ -156,9 +132,9 @@ namespace Mono.Net.Security.Private
                        return Impl.AuthenticateAsServerAsync (serverCertificate);
                }
 
-               public Task AuthenticateAsServerAsync (X509Certificate serverCertificate, bool clientCertificateRequired, XSslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public Task AuthenticateAsServerAsync (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, (SslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public void Flush ()
@@ -201,8 +177,8 @@ namespace Mono.Net.Security.Private
                        Impl.EndWrite (asyncResult);
                }
 
-               public XTransportContext TransportContext {
-                       get { return (XTransportContext)(object)Impl.TransportContext; }
+               public TransportContext TransportContext {
+                       get { return Impl.TransportContext; }
                }
 
                public bool IsAuthenticated {
@@ -225,24 +201,24 @@ namespace Mono.Net.Security.Private
                        get { return Impl.IsServer; }
                }
 
-               public XCipherAlgorithmType CipherAlgorithm {
-                       get { return (XCipherAlgorithmType)Impl.CipherAlgorithm; }
+               public CipherAlgorithmType CipherAlgorithm {
+                       get { return Impl.CipherAlgorithm; }
                }
 
                public int CipherStrength {
                        get { return Impl.CipherStrength; }
                }
 
-               public XHashAlgorithmType HashAlgorithm {
-                       get { return (XHashAlgorithmType)Impl.HashAlgorithm; }
+               public HashAlgorithmType HashAlgorithm {
+                       get { return Impl.HashAlgorithm; }
                }
 
                public int HashStrength {
                        get { return Impl.HashStrength; }
                }
 
-               public XExchangeAlgorithmType KeyExchangeAlgorithm {
-                       get { return (XExchangeAlgorithmType)Impl.KeyExchangeAlgorithm; }
+               public ExchangeAlgorithmType KeyExchangeAlgorithm {
+                       get { return Impl.KeyExchangeAlgorithm; }
                }
 
                public int KeyExchangeStrength {
@@ -274,8 +250,8 @@ namespace Mono.Net.Security.Private
                        Impl.SetLength (value);
                }
 
-               public XAuthenticatedStream AuthenticatedStream {
-                       get { return (XAuthenticatedStream)(Stream)Impl.AuthenticatedStream; }
+               public AuthenticatedStream AuthenticatedStream {
+                       get { return Impl.AuthenticatedStream; }
                }
 
                public int ReadTimeout {
@@ -304,8 +280,8 @@ namespace Mono.Net.Security.Private
                        get { return Impl.RemoteCertificate; }
                }
 
-               public XSslProtocols SslProtocol {
-                       get { return (XSslProtocols)Impl.SslProtocol; }
+               public SslProtocols SslProtocol {
+                       get { return Impl.SslProtocol; }
                }
 
                public MSI.MonoTlsProvider Provider {
index 92f88fe1e0559344bd8ad7bfa0c5d4ebb28c87af..0cf6d394bb7da92c8b500c4c13e2a17db3511f09 100644 (file)
@@ -26,9 +26,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -38,17 +35,6 @@ using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XSslProtocols = PrebuiltSystem::System.Security.Authentication.SslProtocols;
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XSslProtocols = System.Security.Authentication.SslProtocols;
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
-
-using CipherAlgorithmType = System.Security.Authentication.CipherAlgorithmType;
-using HashAlgorithmType = System.Security.Authentication.HashAlgorithmType;
-using ExchangeAlgorithmType = System.Security.Authentication.ExchangeAlgorithmType;
 
 using System;
 using System.IO;
@@ -84,9 +70,9 @@ namespace Mono.Net.Security.Private
                        Impl.AuthenticateAsClient (targetHost);
                }
 
-               public void AuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public void AuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsClient (targetHost, (XX509CertificateCollection)(object)clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public IAsyncResult BeginAuthenticateAsClient (string targetHost, AsyncCallback asyncCallback, object asyncState)
@@ -94,9 +80,9 @@ namespace Mono.Net.Security.Private
                        return Impl.BeginAuthenticateAsClient (targetHost, asyncCallback, asyncState);
                }
 
-               public IAsyncResult BeginAuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
+               public IAsyncResult BeginAuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsClient (targetHost, (XX509CertificateCollection)(object)clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public void EndAuthenticateAsClient (IAsyncResult asyncResult)
@@ -111,7 +97,7 @@ namespace Mono.Net.Security.Private
 
                public void AuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, AsyncCallback asyncCallback, object asyncState)
@@ -121,7 +107,7 @@ namespace Mono.Net.Security.Private
 
                public IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public void EndAuthenticateAsServer (IAsyncResult asyncResult)
@@ -134,9 +120,9 @@ namespace Mono.Net.Security.Private
                        return Impl.AuthenticateAsClientAsync (targetHost);
                }
 
-               public Task AuthenticateAsClientAsync (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public Task AuthenticateAsClientAsync (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public Task AuthenticateAsServerAsync (X509Certificate serverCertificate)
@@ -146,7 +132,7 @@ namespace Mono.Net.Security.Private
 
                public Task AuthenticateAsServerAsync (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public void Flush ()
@@ -190,7 +176,7 @@ namespace Mono.Net.Security.Private
                }
 
                public TransportContext TransportContext {
-                       get { return (TransportContext)(object)Impl.TransportContext; }
+                       get { return Impl.TransportContext; }
                }
 
                public bool IsAuthenticated {
@@ -263,7 +249,7 @@ namespace Mono.Net.Security.Private
                }
 
                public AuthenticatedStream AuthenticatedStream {
-                       get { return (AuthenticatedStream)(object)Impl.AuthenticatedStream; }
+                       get { return Impl.AuthenticatedStream; }
                }
 
                public int ReadTimeout {
diff --git a/mcs/class/System/Mono.Net.Security/MonoTlsProviderFactory.MonoTouch.opt.cs b/mcs/class/System/Mono.Net.Security/MonoTlsProviderFactory.MonoTouch.opt.cs
deleted file mode 100644 (file)
index b8c5d6d..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#if MONOTOUCH || XAMMAC
-
-// this file is a shim to enable compiling monotouch profiles without mono-extensions
-namespace Mono.Net.Security
-{
-       static partial class MonoTlsProviderFactory
-       {
-               static IMonoTlsProvider CreateDefaultProvider ()
-               {
-                       throw new System.NotSupportedException ();
-               }
-       }
-}
-
-#endif
index 1a0c2bc584290d3356358948d9beb48938e93cb9..c4b17abcd0ee93d2c9f98af837dc3064598fd773 100644 (file)
@@ -69,7 +69,7 @@ namespace Mono.Net.Security
                                        return currentProvider;
 
                                try {
-                                       defaultProvider = CreateDefaultProvider ();
+                                       defaultProvider = GetDefaultProviderInternal ();
                                } catch (Exception ex) {
                                        throw new NotSupportedException ("TLS Support not available.", ex);
                                }
@@ -174,6 +174,8 @@ namespace Mono.Net.Security
                                providerRegistration = new Dictionary<string,string> ();
                                providerRegistration.Add ("newtls", "Mono.Security.Providers.NewTls.NewTlsProvider, Mono.Security.Providers.NewTls, Version=4.0.0.0, Culture=neutral, PublicKeyToken=0738eb9f132ed756");
                                providerRegistration.Add ("oldtls", "Mono.Security.Providers.OldTls.OldTlsProvider, Mono.Security.Providers.OldTls, Version=4.0.0.0, Culture=neutral, PublicKeyToken=0738eb9f132ed756");
+                               providerRegistration.Add ("boringtls", "Xamarin.BoringTls.BoringTlsProvider, Xamarin.BoringTls, Version=4.0.0.0, Culture=neutral, PublicKeyToken=672c06b0b8f05406");
+                               X509Helper2.Initialize ();
                        }
                }
 
diff --git a/mcs/class/System/Mono.Net.Security/MonoTlsProviderFactoryExt.cs b/mcs/class/System/Mono.Net.Security/MonoTlsProviderFactoryExt.cs
new file mode 100644 (file)
index 0000000..f9f939b
--- /dev/null
@@ -0,0 +1,22 @@
+// Copyright 2015 Xamarin Inc. All rights reserved.
+
+using System;
+using MSI = Mono.Security.Interface;
+
+namespace Mono.Net.Security
+{
+       static partial class MonoTlsProviderFactory
+       {
+               static IMonoTlsProvider CreateDefaultProvider ()
+               {
+                       #if SECURITY_DEP
+                       MSI.MonoTlsProvider provider = null;
+                       if (MSI.MonoTlsProviderFactory._PrivateFactoryDelegate != null)
+                               provider = MSI.MonoTlsProviderFactory._PrivateFactoryDelegate ();
+                       if (provider != null)
+                               return new Private.MonoTlsProviderWrapper (provider);
+                       #endif
+                       return null;
+               }
+       }
+}
index b0ae5d82c724627ca2360a856b159af606f23104..94f86ca7e747ce244abda4cc8846ce821256270b 100644 (file)
@@ -26,9 +26,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -38,13 +35,6 @@ using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XHttpWebRequest = PrebuiltSystem::System.Net.HttpWebRequest;
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XHttpWebRequest = System.Net.HttpWebRequest;
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System;
 using System.IO;
@@ -84,13 +74,13 @@ namespace Mono.Net.Security.Private
 
                MSI.IMonoTlsContext IMonoTlsProvider.CreateTlsContext (
                        string hostname, bool serverMode, MSI.TlsProtocols protocolFlags,
-                       X509Certificate serverCertificate, XX509CertificateCollection clientCertificates,
+                       X509Certificate serverCertificate, X509CertificateCollection clientCertificates,
                        bool remoteCertRequired, bool checkCertName, bool checkCertRevocationStatus,
                        MSI.MonoEncryptionPolicy encryptionPolicy, MSI.MonoTlsSettings settings)
                {
                        return CreateTlsContextImpl (
                                hostname, serverMode, protocolFlags,
-                               serverCertificate, (X509CertificateCollection)(object)clientCertificates,
+                               serverCertificate, clientCertificates,
                                remoteCertRequired, encryptionPolicy, settings);
                }
 
@@ -102,13 +92,13 @@ namespace Mono.Net.Security.Private
 
                internal override MSI.IMonoTlsContext CreateTlsContext (
                        string hostname, bool serverMode, MSI.TlsProtocols protocolFlags,
-                       X509Certificate serverCertificate, XX509CertificateCollection clientCertificates,
+                       X509Certificate serverCertificate, X509CertificateCollection clientCertificates,
                        bool remoteCertRequired, MSI.MonoEncryptionPolicy encryptionPolicy,
                        MSI.MonoTlsSettings settings)
                {
                        return CreateTlsContextImpl (
                                hostname, serverMode, (MSI.TlsProtocols)protocolFlags,
-                               serverCertificate, (X509CertificateCollection)(object)clientCertificates,
+                               serverCertificate, clientCertificates,
                                remoteCertRequired, (MSI.MonoEncryptionPolicy)encryptionPolicy,
                                settings);
                }
index e2ec0f5a01318b9fefbdfafab0df60f45450c8a3..15283200590899b85f606eb3a2acfc9a08c6a9bb 100644 (file)
@@ -26,9 +26,6 @@
 
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -38,13 +35,6 @@ using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XHttpWebRequest = PrebuiltSystem::System.Net.HttpWebRequest;
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XHttpWebRequest = System.Net.HttpWebRequest;
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System;
 using System.IO;
@@ -86,13 +76,13 @@ namespace Mono.Net.Security.Private
 
                public MSI.IMonoTlsContext CreateTlsContext (
                        string hostname, bool serverMode, MSI.TlsProtocols protocolFlags,
-                       X509Certificate serverCertificate, XX509CertificateCollection clientCertificates,
+                       X509Certificate serverCertificate, X509CertificateCollection clientCertificates,
                        bool remoteCertRequired, bool checkCertName, bool checkCertRevocationStatus,
                        MSI.MonoEncryptionPolicy encryptionPolicy, MSI.MonoTlsSettings settings)
                {
                        return provider.CreateTlsContext (
                                hostname, serverMode, protocolFlags,
-                               serverCertificate, (XX509CertificateCollection)(object)clientCertificates,
+                               serverCertificate, clientCertificates,
                                remoteCertRequired, (MSI.MonoEncryptionPolicy)encryptionPolicy,
                                settings);
                }
index 96f5933dfb7ba0608ad4f5827671eb23bb390d37..58479df9fba6942c75eff0c548ec913f95f84cc0 100644 (file)
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MonoSecurity::Mono.Security.Interface;
 #else
 using Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
 #endif
-#endif
 
 using System;
 using System.IO;
@@ -104,7 +97,7 @@ namespace Mono.Net.Security
 
                        try {
                                sslStream.AuthenticateAsClient (
-                                       request.Address.Host, (XX509CertificateCollection)(object)request.ClientCertificates,
+                                       request.Address.Host, request.ClientCertificates,
                                        (SslProtocols)ServicePointManager.SecurityProtocol,
                                        ServicePointManager.CheckCertificateRevocationList);
 
index dd67b660bef8f9212278f53c7bf6fecb62210068..55969818a8b5d4299725c0e5f81129020d1f9366 100644 (file)
@@ -3,9 +3,6 @@
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MonoSecurity::Mono.Security.Interface;
@@ -16,13 +13,8 @@ using Mono.Security.Interface;
 using MSX = Mono.Security.X509;
 using Mono.Security.X509.Extensions;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-using XX509Chain = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509Chain;
-#else
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
 using XX509Chain = System.Security.Cryptography.X509Certificates.X509Chain;
-#endif
 
 using System;
 using System.Net;
@@ -121,7 +113,9 @@ namespace Mono.Net.Security
                static bool CheckUsage (XX509CertificateCollection certs, string host, ref SslPolicyErrors errors, ref int status11)
                {
 #if !MONOTOUCH
-                       var leaf = (X509Certificate2)certs[0];
+                       var leaf = certs[0] as X509Certificate2;
+                       if (leaf == null)
+                               leaf = new X509Certificate2 (certs[0]);
                        // for OSX and iOS we're using the native API to check for the SSL server policy and host names
                        if (!is_macosx) {
                                if (!CheckCertificateUsage (leaf)) {
diff --git a/mcs/class/System/Mono.Security.Interface/MonoTlsProviderFactoryExt.cs b/mcs/class/System/Mono.Security.Interface/MonoTlsProviderFactoryExt.cs
new file mode 100644 (file)
index 0000000..e902c80
--- /dev/null
@@ -0,0 +1,9 @@
+namespace Mono.Security.Interface
+{
+       public delegate MonoTlsProvider MonoTlsProviderFactoryDelegate ();
+
+       static partial class MonoTlsProviderFactory
+       {
+               public static MonoTlsProviderFactoryDelegate _PrivateFactoryDelegate;
+       }
+}
index 629617f60312967c794b5f3a526de8eed72ed531..a0cb8d5019380a67cb9c638fcb083bcdf085cf87 100644 (file)
@@ -28,9 +28,6 @@
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MX = MonoSecurity::Mono.Security.X509;
@@ -39,11 +36,6 @@ using MonoSecurity::Mono.Security.Interface;
 using MX = Mono.Security.X509;
 using Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System.Runtime.InteropServices;
 using System.Security.Authentication.ExtendedProtection;
@@ -73,7 +65,7 @@ namespace System.Net.Security
 
        internal static class GlobalSSPI
        {
-               internal static SSPIInterface Create (string hostname, bool serverMode, SchProtocols protocolFlags, X509Certificate serverCertificate, XX509CertificateCollection clientCertificates,
+               internal static SSPIInterface Create (string hostname, bool serverMode, SchProtocols protocolFlags, X509Certificate serverCertificate, X509CertificateCollection clientCertificates,
                                                           bool remoteCertRequired, bool checkCertName, bool checkCertRevocationStatus, EncryptionPolicy encryptionPolicy,
                                                           LocalCertSelectionCallback certSelectionDelegate, RemoteCertValidationCallback remoteValidationCallback, SSPIConfiguration userConfig)
                {
@@ -226,7 +218,7 @@ namespace System.Net.Security
 
                internal static X509Certificate2 GetRemoteCertificate (SafeDeleteContext safeContext, out X509Certificate2Collection remoteCertificateStore)
                {
-                       XX509CertificateCollection monoCollection;
+                       X509CertificateCollection monoCollection;
                        if (safeContext == null || safeContext.IsInvalid) {
                                remoteCertificateStore = null;
                                return null;
index 2e739291d3412dce486ffaa9063cfa6711afdfd4..2abea7293f9ecff95358518babcdca29382258f9 100644 (file)
@@ -29,9 +29,6 @@
 //
 
 #if CONFIGURATION_DEP
-extern alias PrebuiltSystem;
-using TypeDescriptor = PrebuiltSystem.System.ComponentModel.TypeDescriptor;
-
 using System;
 using System.Collections.Generic;
 using System.ComponentModel;
index 57aa6b19880683f76b923e984e4d92e4fc3d81eb..7a0bd6ef5dff7a556ba5159e668a4887b9b1acb6 100644 (file)
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 
-#if CONFIGURATION_DEP
-extern alias PrebuiltSystem;
-using NameValueCollection = PrebuiltSystem.System.Collections.Specialized.NameValueCollection;
-#endif
-
 using System.Reflection;
 using System.Collections.Specialized;
 
index 58ebcd7a5f73ee56af0dc156aee11fcd6c1df9f1..6b12f95425b8433a45d4def40764bc34067ccb2d 100644 (file)
 // Copyright (C) 2005, 2006 Novell, Inc (http://www.novell.com)
 //
 
-#if CONFIGURATION_DEP
-extern alias PrebuiltSystem;
-using NameValueCollection = PrebuiltSystem.System.Collections.Specialized.NameValueCollection;
-#endif
 #if CONFIGURATION_DEP
 using System.IO;
 using System.Xml.Serialization;
index 968532966e3d13de35882a06802f6fbbe507413c..9b2f8e9986b8768ff7ae95a95620bbb19cb9d7a1 100644 (file)
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 
-#if CONFIGURATION_DEP
-extern alias PrebuiltSystem;
-using NameValueCollection = PrebuiltSystem.System.Collections.Specialized.NameValueCollection;
-#endif
-
 using System;
 using System.Collections;
 using System.Collections.Specialized;
index 31d56ce09eb38acf77a1e3a2a9ab1466b66b1266..d74a226f1e77042ed2668b56212b96a03e6a22b8 100644 (file)
 
 #if CONFIGURATION_DEP
 
-extern alias PrebuiltSystem;
-
 using System;
 using System.Collections;
 using System.Collections.Generic;
+using System.Collections.Specialized;
 using System.Configuration;
 using System.Globalization;
 using System.IO;
@@ -42,8 +41,6 @@ using System.Security.Cryptography;
 using System.Text;
 using System.Xml;
 
-using NameValueCollection = PrebuiltSystem.System.Collections.Specialized.NameValueCollection;
-
 namespace System.Configuration
 {
        // location to store user configuration settings.
index d0ca5ab0a48b838a95eb18378f4e3209b4f89859..10664ca266bc2aef89b312b67d4e00fb82edb00e 100644 (file)
 //
 
 #if CONFIGURATION_DEP
-#if CONFIGURATION_DEP
-extern alias PrebuiltSystem;
-using NameValueCollection = PrebuiltSystem.System.Collections.Specialized.NameValueCollection;
-#endif
 
 using System;
 using System.Collections.Specialized;
index 2bf4cab23c6e5641bcf5c351a09c2c7444058b10..fb31ace627b679a46f3b9eece4154858108a0c14 100644 (file)
@@ -255,10 +255,10 @@ namespace System.Diagnostics {
                                WritePrefix ();
                        }
 
-                       WriteDebugString (message);
-
                        if (Debugger.IsLogging())
                                Debugger.Log (0, null, message);
+                       else
+                               WriteDebugString (message);
 
                        WriteLogFile (message, LogFileName);
                }
index 57b8e669160aca8d9934afb06f6d77f839158532..6e929543aed5fec2f03a7c7dde270c307a54b91d 100644 (file)
@@ -74,7 +74,7 @@ namespace System.Diagnostics
 
                /* Private constructor called from other methods */
                private Process (SafeProcessHandle handle, int id) {
-                       m_processHandle = handle;
+                       SetProcessHandle (handle);
                        SetProcessId (id);
                }
 
@@ -302,7 +302,7 @@ namespace System.Diagnostics
                [DesignerSerializationVisibility (DesignerSerializationVisibility.Hidden)]
                [MonitoringDescription ("The session ID for this process.")]
                public int SessionId {
-                       get { throw new NotImplementedException (); }
+                       get { return 0; }
                }
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
@@ -606,13 +606,9 @@ namespace System.Diagnostics
                                throw new Win32Exception (-proc_info.pid);
                        }
 
-                       m_processHandle = new SafeProcessHandle (proc_info.process_handle, true);
-                       haveProcessHandle = true;
+                       SetProcessHandle (new SafeProcessHandle (proc_info.process_handle, true));
                        SetProcessId (proc_info.pid);
 
-                       if (watchForExit)
-                               EnsureWatchingForExit ();
-
                        return ret;
                }
 
@@ -771,8 +767,7 @@ namespace System.Diagnostics
                                }
                        }
 
-                       m_processHandle = new SafeProcessHandle (proc_info.process_handle, true);
-                       haveProcessHandle = true;
+                       SetProcessHandle (new SafeProcessHandle (proc_info.process_handle, true));
                        SetProcessId (proc_info.pid);
                        
                        if (startInfo.RedirectStandardInput) {
@@ -808,9 +803,6 @@ namespace System.Diagnostics
                                standardError = new StreamReader (new FileStream (stderr_read, FileAccess.Read, true, 8192), stderrEncoding, true);
                        }
 
-                       if (watchForExit)
-                               EnsureWatchingForExit ();
-
                        return true;
                }
 
index b2d964ceb5e0cc451618a2dfc914fd78f8dbc446..778671764ea91a8f8b9bcc563e60b0b68d9d0fdd 100644 (file)
@@ -300,11 +300,14 @@ namespace System.IO {
                        else
                                fullPathNoLastSlash = fsw.FullPath;
                                
-                       // GetFilenameFromFd() returns the *realpath* which can be different than fsw.FullPath because symlinks.
+                       // realpath() returns the *realpath* which can be different than fsw.FullPath because symlinks.
                        // If so, introduce a fixup step.
-                       int fd = open (fullPathNoLastSlash, O_EVTONLY, 0);
-                       var resolvedFullPath = GetFilenameFromFd (fd);
-                       close (fd);
+                       var sb = new StringBuilder (__DARWIN_MAXPATHLEN);
+                       if (realpath(fsw.FullPath, sb) == IntPtr.Zero) {
+                               var errMsg = String.Format ("realpath({0}) failed, error code = '{1}'", fsw.FullPath, Marshal.GetLastWin32Error ());
+                               throw new IOException (errMsg);
+                       }
+                       var resolvedFullPath = sb.ToString();
 
                        if (resolvedFullPath != fullPathNoLastSlash)
                                fixupPath = resolvedFullPath;
@@ -317,10 +320,17 @@ namespace System.IO {
                        var eventBuffer = new kevent[0]; // we don't want to take any events from the queue at this point
                        var changes = CreateChangeList (ref initialFds);
 
-                       int numEvents = kevent (conn, changes, changes.Length, eventBuffer, eventBuffer.Length, ref immediate_timeout);
+                       int numEvents;
+                       int errno = 0;
+                       do {
+                               numEvents = kevent (conn, changes, changes.Length, eventBuffer, eventBuffer.Length, ref immediate_timeout);
+                               if (numEvents == -1) {
+                                       errno = Marshal.GetLastWin32Error ();
+                               }
+                       } while (numEvents == -1 && errno == EINTR);
 
                        if (numEvents == -1) {
-                               var errMsg = String.Format ("kevent() error at initial event registration, error code = '{0}'", Marshal.GetLastWin32Error ());
+                               var errMsg = String.Format ("kevent() error at initial event registration, error code = '{0}'", errno);
                                throw new IOException (errMsg);
                        }
                }
@@ -384,9 +394,10 @@ namespace System.IO {
                                        // Stop () signals us to stop by closing the connection
                                        if (requestStop)
                                                break;
-                                       if (++retries == 3)
+                                       int errno = Marshal.GetLastWin32Error ();
+                                       if (errno != EINTR && ++retries == 3)
                                                throw new IOException (String.Format (
-                                                       "persistent kevent() error, error code = '{0}'", Marshal.GetLastWin32Error ()));
+                                                       "persistent kevent() error, error code = '{0}'", errno));
 
                                        continue;
                                }
@@ -606,14 +617,14 @@ namespace System.IO {
                                return;
 
                        // e.Name
-                       string name = path.Substring (fullPathNoLastSlash.Length + 1); 
+                       string name = (path.Length > fullPathNoLastSlash.Length) ? path.Substring (fullPathNoLastSlash.Length + 1) : String.Empty;
 
                        // only post events that match filter pattern. check both old and new paths for renames
                        if (!fsw.Pattern.IsMatch (path) && (newPath == null || !fsw.Pattern.IsMatch (newPath)))
                                return;
                                
                        if (action == FileAction.RenamedNewName) {
-                               string newName = newPath.Substring (fullPathNoLastSlash.Length + 1);
+                               string newName = (newPath.Length > fullPathNoLastSlash.Length) ? newPath.Substring (fullPathNoLastSlash.Length + 1) : String.Empty;
                                renamed = new RenamedEventArgs (WatcherChangeTypes.Renamed, fsw.Path, newName, name);
                        }
                                
@@ -646,6 +657,7 @@ namespace System.IO {
                const int O_EVTONLY = 0x8000;
                const int F_GETPATH = 50;
                const int __DARWIN_MAXPATHLEN = 1024;
+               const int EINTR = 4;
                static readonly kevent[] emptyEventList = new System.IO.kevent[0];
                int maxFds = Int32.MaxValue;
 
@@ -665,19 +677,22 @@ namespace System.IO {
                string fixupPath = null;
                string fullPathNoLastSlash = null;
 
-               [DllImport ("libc", EntryPoint="fcntl", CharSet=CharSet.Auto, SetLastError=true)]
+               [DllImport ("libc", CharSet=CharSet.Auto, SetLastError=true)]
                static extern int fcntl (int file_names_by_descriptor, int cmd, StringBuilder sb);
 
-               [DllImport ("libc")]
+               [DllImport ("libc", CharSet=CharSet.Auto, SetLastError=true)]
+               static extern IntPtr realpath (string pathname, StringBuilder sb);
+
+               [DllImport ("libc", SetLastError=true)]
                extern static int open (string path, int flags, int mode_t);
 
                [DllImport ("libc")]
                extern static int close (int fd);
 
-               [DllImport ("libc")]
+               [DllImport ("libc", SetLastError=true)]
                extern static int kqueue ();
 
-               [DllImport ("libc")]
+               [DllImport ("libc", SetLastError=true)]
                extern static int kevent (int kq, [In]kevent[] ev, int nchanges, [Out]kevent[] evtlist, int nevents, [In] ref timespec time);
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
index 0e89b187d1a97a216d0677c1cfb612e88cfb97eb..ff881b00bcc9a6df8a457c16e23d134a2ebcef16 100644 (file)
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using X509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using X509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 using System.Security.Cryptography.X509Certificates;
 #endif
 
index 5d0d9b75471a55d28cf32dbf9157559087bae2c9..9b77646d7b1502b669d501fcd04bd3e9197c687c 100644 (file)
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 #if SECURITY_DEP && !MONO_FEATURE_NEW_TLS
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-using X509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System.Security.Cryptography.X509Certificates;
 
index 652c91e143fc6d4e18463b192fcfae99c4f9d07b..9238428b1f3841de180dc5f09f3944336a9d82d1 100644 (file)
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 #if !MONO_FEATURE_NEW_TLS
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-using X509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System.Security.Cryptography.X509Certificates;
 
index 53e6d2918577369637da3f522ced844a316bb82a..59e741722b67b820861fb63af0005b004087397c 100644 (file)
@@ -27,9 +27,6 @@
 #if !MONO_FEATURE_NEW_TLS
 #if SECURITY_DEP
 
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
@@ -39,13 +36,6 @@ using MonoSecurity::Mono.Security.Interface;
 #else
 using Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XSslProtocols = PrebuiltSystem::System.Security.Authentication.SslProtocols;
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XSslProtocols = System.Security.Authentication.SslProtocols;
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using CipherAlgorithmType = System.Security.Authentication.CipherAlgorithmType;
 using HashAlgorithmType = System.Security.Authentication.HashAlgorithmType;
@@ -80,7 +70,7 @@ namespace System.Net.Security
 
        internal delegate X509Certificate LocalCertSelectionCallback (
                string targetHost,
-               XX509CertificateCollection localCertificates,
+               X509CertificateCollection localCertificates,
                X509Certificate remoteCertificate,
                string[] acceptableIssuers);
 
@@ -146,9 +136,9 @@ namespace System.Net.Security
                        Impl.AuthenticateAsClient (targetHost);
                }
 
-               public virtual void AuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public virtual void AuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsClient (targetHost, (XX509CertificateCollection)(object)clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                // [HostProtection (ExternalThreading=true)]
@@ -158,9 +148,9 @@ namespace System.Net.Security
                }
 
                // [HostProtection (ExternalThreading=true)]
-               public virtual IAsyncResult BeginAuthenticateAsClient (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
+               public virtual IAsyncResult BeginAuthenticateAsClient (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsClient (targetHost, (XX509CertificateCollection)(object)clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsClient (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public virtual void EndAuthenticateAsClient (IAsyncResult asyncResult)
@@ -175,7 +165,7 @@ namespace System.Net.Security
 
                public virtual void AuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       Impl.AuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                // [HostProtection (ExternalThreading=true)]
@@ -186,7 +176,7 @@ namespace System.Net.Security
 
                public virtual IAsyncResult BeginAuthenticateAsServer (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation, AsyncCallback asyncCallback, object asyncState)
                {
-                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
+                       return Impl.BeginAuthenticateAsServer (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation, asyncCallback, asyncState);
                }
 
                public virtual void EndAuthenticateAsServer (IAsyncResult asyncResult)
@@ -206,9 +196,9 @@ namespace System.Net.Security
                        return Impl.AuthenticateAsClientAsync (targetHost);
                }
 
-               public virtual Task AuthenticateAsClientAsync (string targetHost, XX509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
+               public virtual Task AuthenticateAsClientAsync (string targetHost, X509CertificateCollection clientCertificates, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsClientAsync (targetHost, clientCertificates, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public virtual Task AuthenticateAsServerAsync (X509Certificate serverCertificate)
@@ -218,7 +208,7 @@ namespace System.Net.Security
 
                public virtual Task AuthenticateAsServerAsync (X509Certificate serverCertificate, bool clientCertificateRequired, SslProtocols enabledSslProtocols, bool checkCertificateRevocation)
                {
-                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, (XSslProtocols)enabledSslProtocols, checkCertificateRevocation);
+                       return Impl.AuthenticateAsServerAsync (serverCertificate, clientCertificateRequired, enabledSslProtocols, checkCertificateRevocation);
                }
 
                public override bool IsAuthenticated {
index e0f8569969f680c662d71a55e2019a5650015656..33f83eccec481a4768b360eb7a4552b41b38f936 100644 (file)
@@ -16,6 +16,7 @@ namespace System.Net.Sockets {
        sealed class SafeSocketHandle : SafeHandleZeroOrMinusOneIsInvalid {
 
                List<Thread> blocking_threads;
+               bool in_cleanup;
 
                const int SOCKET_CLOSED = 10004;
 
@@ -43,32 +44,36 @@ namespace System.Net.Sockets {
 #endif
 
                        if (blocking_threads != null) {
-                               int abort_attempts = 0;
-                               while (blocking_threads.Count > 0) {
-                                       if (abort_attempts++ >= ABORT_RETRIES) {
-                                               if (THROW_ON_ABORT_RETRIES)
-                                                       throw new Exception ("Could not abort registered blocking threads before closing socket.");
-
-                                               // Attempts to close the socket safely failed.
-                                               // We give up, and close the socket with pending blocking system calls.
-                                               // This should not occur, nonetheless if it does this avoids an endless loop.
-                                               break;
-                                       }
-
-                                       /*
-                                        * This method can be called by the DangerousRelease inside RegisterForBlockingSyscall
-                                        * When this happens blocking_threads contains the current thread.
-                                        * We can safely close the socket and throw SocketException in RegisterForBlockingSyscall
-                                        * before the blocking system call.
-                                        */
-                                       lock (blocking_threads) {
+                               lock (blocking_threads) {
+                                       int abort_attempts = 0;
+                                       while (blocking_threads.Count > 0) {
+                                               if (abort_attempts++ >= ABORT_RETRIES) {
+                                                       if (THROW_ON_ABORT_RETRIES)
+                                                               throw new Exception ("Could not abort registered blocking threads before closing socket.");
+
+                                                       // Attempts to close the socket safely failed.
+                                                       // We give up, and close the socket with pending blocking system calls.
+                                                       // This should not occur, nonetheless if it does this avoids an endless loop.
+                                                       break;
+                                               }
+
+                                               /*
+                                               * This method can be called by the DangerousRelease inside RegisterForBlockingSyscall
+                                               * When this happens blocking_threads contains the current thread.
+                                               * We can safely close the socket and throw SocketException in RegisterForBlockingSyscall
+                                               * before the blocking system call.
+                                               */
                                                if (blocking_threads.Count == 1 && blocking_threads[0] == Thread.CurrentThread)
                                                        break;
-                                       }
 
-                                       AbortRegisteredThreads ();
-                                       // Sleep so other threads can resume
-                                       Thread.Sleep (1);
+                                               // abort registered threads
+                                               foreach (var t in blocking_threads)
+                                                       Socket.cancel_blocking_socket_operation (t);
+
+                                               // Sleep so other threads can resume
+                                               in_cleanup = true;
+                                               Monitor.Wait (blocking_threads, 100);
+                                       }
                                }
                        }
 
@@ -105,16 +110,8 @@ namespace System.Net.Sockets {
                        //If this NRE, we're in deep problems because Register Must have
                        lock (blocking_threads) {
                                blocking_threads.Remove (Thread.CurrentThread);
-                       }
-               }
-
-               void AbortRegisteredThreads () {
-                       if (blocking_threads == null)
-                               return;
-
-                       lock (blocking_threads) {
-                               foreach (var t in blocking_threads)
-                                       Socket.cancel_blocking_socket_operation (t);
+                               if (in_cleanup && blocking_threads.Count == 0)
+                                       Monitor.Pulse (blocking_threads);
                        }
                }
        }
index 9726b91358b2ffeb1030370681e901b519a6ee8d..5400d73b87e7e6fee4d7d365260f00d7797f81d9 100644 (file)
@@ -73,7 +73,7 @@ namespace System.Net {
                        SocketAsyncEventArgs args = new SocketAsyncEventArgs ();
                        args.UserToken = this;
                        args.Completed += OnAccept;
-                       sock.AcceptAsync (args);
+                       Accept (sock, args);
                        prefixes = new Hashtable ();
                        unregistered = new Dictionary<HttpConnection, HttpConnection> ();
                }
@@ -82,28 +82,25 @@ namespace System.Net {
                        get { return listener; }
                }
 
-               static void OnAccept (object sender, EventArgs e)
+               static void Accept (Socket socket, SocketAsyncEventArgs e) {
+                       e.AcceptSocket = null;
+                       var asyn = socket.AcceptAsync(e);
+                       if (!asyn) {
+                               ProcessAccept(e);
+                       }
+               }
+
+
+               static void ProcessAccept (SocketAsyncEventArgs args) 
                {
-                       SocketAsyncEventArgs args = (SocketAsyncEventArgs) e;
-                       EndPointListener epl = (EndPointListener) args.UserToken;
                        Socket accepted = null;
-                       if (args.SocketError == SocketError.Success) {
+                       if (args.SocketError == SocketError.Success)
                                accepted = args.AcceptSocket;
-                               args.AcceptSocket = null;
-                       }
 
-                       try {
-                               if (epl.sock != null)
-                                       epl.sock.AcceptAsync (args);
-                       } catch {
-                               if (accepted != null) {
-                                       try {
-                                               accepted.Close ();
-                                       } catch {}
-                                       accepted = null;
-                               }
-                       } 
+                       EndPointListener epl = (EndPointListener) args.UserToken;
+
 
+                       Accept (epl.sock, args);
                        if (accepted == null)
                                return;
 
@@ -118,7 +115,12 @@ namespace System.Net {
                        conn.BeginReadRequest ();
                }
 
-               internal void RemoveConnection (HttpConnection conn)
+               static void OnAccept (object sender, SocketAsyncEventArgs e) 
+               {
+                       ProcessAccept (e);
+               }
+
+               internal void RemoveConnection (HttpConnection conn) 
                {
                        lock (unregistered) {
                                unregistered.Remove (conn);
index 885eaf3ea3df14566dcf0a32bf21e653d1314be9..b9940eb07d89585b683f2904aa1b0fb49aa84157 100644 (file)
 #if MONO_SECURITY_ALIAS
 extern alias MonoSecurity;
 #endif
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
 #if MONO_SECURITY_ALIAS
 using MSI = MonoSecurity::Mono.Security.Interface;
 #else
 using MSI = Mono.Security.Interface;
 #endif
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
-using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System.IO;
 using System.Net.Sockets;
index 769195a2b3ec4c965278d9ed8aa7670388d5e800..f1c47802cb94bef9e16534919ff1d10aba148b8c 100644 (file)
@@ -403,7 +403,7 @@ namespace System.Net {
                }
 
                public bool IsLocal {
-                       get { return IPAddress.IsLoopback (RemoteEndPoint.Address); }
+                       get { return LocalEndPoint.Address.Equals (RemoteEndPoint.Address); }
                }
 
                public bool IsSecureConnection {
index 71eb71e31062c3b5704713a2573ef4caf2fda9c3..e0c3ed84318073bd271c8ffa07f2e9b7566554a9 100644 (file)
@@ -27,8 +27,6 @@
 //
 #if CONFIGURATION_DEP
 
-extern alias PrebuiltSystem;
-
 using System;
 using System.Collections;
 using System.Collections.Generic;
@@ -42,8 +40,6 @@ using System.Runtime.Serialization;
 using System.Text;
 using System.Xml;
 
-using TypeConverter = PrebuiltSystem::System.ComponentModel.TypeConverter;
-
 namespace System.Security.Authentication.ExtendedProtection.Configuration
 {
        internal static class ConfigUtil
index 184e586471dd30c167be16eca420d930c5c12bfb..695f5e822209a0964b0c604cdca50c421e48c52c 100644 (file)
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
 #if SECURITY_DEP
-#if MONO_X509_ALIAS
-extern alias PrebuiltSystem;
-#endif
 
-#if MONO_X509_ALIAS
-using XX509CertificateCollection = PrebuiltSystem::System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#else
 using XX509CertificateCollection = System.Security.Cryptography.X509Certificates.X509CertificateCollection;
-#endif
 
 using System;
 using System.Runtime.InteropServices;
@@ -101,16 +94,17 @@ namespace System.Security.Cryptography.X509Certificates {
                        }
                }
 
-               static IntPtr GetCertificate (X509Certificate certificate, out IntPtr dataPtr)
+               static IntPtr GetCertificate (X509Certificate certificate)
                {
-                       var handle = certificate.Handle;
+                       var handle = certificate.Impl.GetNativeAppleCertificate ();
                        if (handle != IntPtr.Zero) {
-                               dataPtr = IntPtr.Zero;
                                CFRetain (handle);
                                return handle;
                        }
-                       dataPtr = MakeCFData (certificate.GetRawCertData ());
-                       return SecCertificateCreateWithData (IntPtr.Zero, dataPtr);
+                       var dataPtr = MakeCFData (certificate.GetRawCertData ());
+                       handle = SecCertificateCreateWithData (IntPtr.Zero, dataPtr);
+                       CFRelease (dataPtr);
+                       return handle;
                }
                
                public static SecTrustResult TrustEvaluateSsl (XX509CertificateCollection certificates, XX509CertificateCollection anchors, string host)
@@ -129,9 +123,7 @@ namespace System.Security.Cryptography.X509Certificates {
                {
                        int certCount = certificates.Count;
                        int anchorCount = anchors != null ? anchors.Count : 0;
-                       IntPtr [] cfDataPtrs = new IntPtr [certCount];
                        IntPtr [] secCerts = new IntPtr [certCount];
-                       IntPtr [] cfDataAnchorPtrs = new IntPtr [anchorCount];
                        IntPtr [] secCertAnchors = new IntPtr [anchorCount];
                        IntPtr certArray = IntPtr.Zero;
                        IntPtr anchorArray = IntPtr.Zero;
@@ -142,13 +134,13 @@ namespace System.Security.Cryptography.X509Certificates {
 
                        try {
                                for (int i = 0; i < certCount; i++) {
-                                       secCerts [i] = GetCertificate (certificates [i], out cfDataPtrs [i]);
+                                       secCerts [i] = GetCertificate (certificates [i]);
                                        if (secCerts [i] == IntPtr.Zero)
                                                return SecTrustResult.Deny;
                                }
 
                                for (int i = 0; i < anchorCount; i++) {
-                                       secCertAnchors [i] = GetCertificate (anchors [i], out cfDataAnchorPtrs [i]);
+                                       secCertAnchors [i] = GetCertificate (anchors [i]);
                                        if (secCertAnchors [i] == IntPtr.Zero)
                                                return SecTrustResult.Deny;
                                }
@@ -170,14 +162,6 @@ namespace System.Security.Cryptography.X509Certificates {
                                code = SecTrustEvaluate (sectrust, out result);
                                return result;
                        } finally {
-                               for (int i = 0; i < certCount; i++)
-                                       if (cfDataPtrs [i] != IntPtr.Zero)
-                                               CFRelease (cfDataPtrs [i]);
-
-                               for (int i = 0; i < anchorCount; i++)
-                                       if (cfDataAnchorPtrs [i] != IntPtr.Zero)
-                                               CFRelease (cfDataAnchorPtrs [i]);
-
                                if (certArray != IntPtr.Zero)
                                        CFRelease (certArray);
 
index 0681e9eb5d7c6c4056b0c3008d8c34104f9db8ee..795f0d04b21acfabb51a09db288cfa3ccfecd274 100644 (file)
@@ -52,6 +52,7 @@ namespace System.Security.Cryptography.X509Certificates {
                        X500DistinguishedNameFlags.UseT61Encoding | X500DistinguishedNameFlags.ForceUTF8Encoding;
 
                private string name;
+               private byte[] canonEncoding;
 
 
                public X500DistinguishedName (AsnEncodedData encodedDistinguishedName)
@@ -122,6 +123,20 @@ namespace System.Security.Cryptography.X509Certificates {
                        name = distinguishedName.name;
                }
 
+               internal X500DistinguishedName (byte[] encoded, byte[] canonEncoding, string name)
+                       : this (encoded)
+               {
+                       this.canonEncoding = canonEncoding;
+                       this.name = name;
+
+                       Oid = new Oid ();
+                       RawData = encoded;
+               }
+
+               internal byte[] CanonicalEncoding {
+                       get { return canonEncoding; }
+               }
+
 
                public string Name {
                        get { return name; }
@@ -215,6 +230,16 @@ namespace System.Security.Cryptography.X509Certificates {
                        if (name2 == null)
                                return false;
 
+                       if (name1.canonEncoding != null && name2.canonEncoding != null) {
+                               if (name1.canonEncoding.Length != name2.canonEncoding.Length)
+                                       return false;
+                               for (int i = 0; i < name1.canonEncoding.Length; i++) {
+                                       if (name1.canonEncoding[i] != name2.canonEncoding[2])
+                                               return false;
+                               }
+                               return true;
+                       }
+
                        X500DistinguishedNameFlags flags = X500DistinguishedNameFlags.UseNewLines | X500DistinguishedNameFlags.DoNotUseQuotes;
                        string[] split = new string[] { Environment.NewLine };
                        string[] parts1 = name1.Decode (flags).Split (split, StringSplitOptions.RemoveEmptyEntries);
index afb81cb1ab77e0488174477741d71bf0e3d766c3..29decab439faa252aeb371c167e754684e7f9ec9 100644 (file)
@@ -44,11 +44,13 @@ using MX = Mono.Security.X509;
 
 using System.IO;
 using System.Text;
+using System.Collections;
 
 namespace System.Security.Cryptography.X509Certificates {
 
        [Serializable]
        public class X509Certificate2 : X509Certificate {
+       
 #if !SECURITY_DEP
                // Used in Mono.Security HttpsClientStream
                public X509Certificate2 (byte[] rawData)
@@ -56,24 +58,20 @@ namespace System.Security.Cryptography.X509Certificates {
                }
 #endif
 #if SECURITY_DEP
-               private bool _archived;
-               private X509ExtensionCollection _extensions;
-               private string _name = String.Empty;
-               private string _serial;
-               private PublicKey _publicKey;
-               private X500DistinguishedName issuer_name;
-               private X500DistinguishedName subject_name;
-               private Oid signature_algorithm;
-
-               private MX.X509Certificate _cert;
+               new internal X509Certificate2Impl Impl {
+                       get {
+                               var impl2 = base.Impl as X509Certificate2Impl;
+                               X509Helper2.ThrowIfContextInvalid (impl2);
+                               return impl2;
+                       }
+               }
 
-               private static string empty_error = Locale.GetText ("Certificate instance is empty.");
+               string friendlyName = string.Empty;
 
                // constructors
 
                public X509Certificate2 ()
                {
-                       _cert = null;
                }
 
                public X509Certificate2 (byte[] rawData)
@@ -128,206 +126,88 @@ namespace System.Security.Cryptography.X509Certificates {
 
                public X509Certificate2 (IntPtr handle) : base (handle) 
                {
-                       _cert = new MX.X509Certificate (base.GetRawCertData ());
+                       throw new NotImplementedException ();
                }
 
                public X509Certificate2 (X509Certificate certificate) 
-                       : base (certificate)
+                       : base (X509Helper2.Import (certificate))
+               {
+               }
+
+               internal X509Certificate2 (X509Certificate2Impl impl)
+                       : base (impl)
                {
-                       _cert = new MX.X509Certificate (base.GetRawCertData ());
                }
 
                // properties
 
                public bool Archived {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               return _archived;
-                       }
-                       set {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               _archived = value;
-                       }
+                       get { return Impl.Archived; }
+                       set { Impl.Archived = true; }
                }
 
                public X509ExtensionCollection Extensions {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               if (_extensions == null)
-                                       _extensions = new X509ExtensionCollection (_cert);
-                               return _extensions;
-                       }
+                       get { return Impl.Extensions; }
                }
 
                public string FriendlyName {
                        get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               return _name;
+                               ThrowIfContextInvalid ();
+                               return friendlyName;
                        }
                        set {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               _name = value;
+                               ThrowIfContextInvalid ();
+                               friendlyName = value;
                        }
                }
 
-               // FIXME - Could be more efficient
                public bool HasPrivateKey {
-                       get { return PrivateKey != null; }
+                       get { return Impl.HasPrivateKey; }
                }
 
                public X500DistinguishedName IssuerName {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               if (issuer_name == null)
-                                       issuer_name = new X500DistinguishedName (_cert.GetIssuerName ().GetBytes ());
-                               return issuer_name;
-                       }
+                       get { return Impl.IssuerName; }
                } 
 
                public DateTime NotAfter {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               return _cert.ValidUntil.ToLocalTime ();
-                       }
+                       get { return Impl.GetValidUntil ().ToLocalTime (); }
                }
 
                public DateTime NotBefore {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               return _cert.ValidFrom.ToLocalTime ();
-                       }
+                       get { return Impl.GetValidFrom ().ToLocalTime (); }
                }
 
                public AsymmetricAlgorithm PrivateKey {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               try {
-                                       if (_cert.RSA != null) {
-                                               RSACryptoServiceProvider rcsp = _cert.RSA as RSACryptoServiceProvider;
-                                               if (rcsp != null)
-                                                       return rcsp.PublicOnly ? null : rcsp;
-
-                                               RSAManaged rsam = _cert.RSA as RSAManaged;
-                                               if (rsam != null)
-                                                       return rsam.PublicOnly ? null : rsam;
-
-                                               _cert.RSA.ExportParameters (true);
-                                               return _cert.RSA;
-                                       } else if (_cert.DSA != null) {
-                                               DSACryptoServiceProvider dcsp = _cert.DSA as DSACryptoServiceProvider;
-                                               if (dcsp != null)
-                                                       return dcsp.PublicOnly ? null : dcsp;
-
-                                               _cert.DSA.ExportParameters (true);
-                                               return _cert.DSA;
-                                       }
-                               }
-                               catch {
-                               }
-                               return null;
-                       }
-                       set {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               // allow NULL so we can "forget" the key associated to the certificate
-                               // e.g. in case we want to export it in another format (see bug #396620)
-                               if (value == null) {
-                                       _cert.RSA = null;
-                                       _cert.DSA = null;
-                               } else  if (value is RSA)
-                                       _cert.RSA = (RSA) value;
-                               else if (value is DSA)
-                                       _cert.DSA = (DSA) value;
-                               else
-                                       throw new NotSupportedException ();
-                       }
+                       get { return Impl.PrivateKey; }
+                       set { Impl.PrivateKey = value; }
                } 
 
                public PublicKey PublicKey {
-                       get { 
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               if (_publicKey == null) {
-                                       try {
-                                               _publicKey = new PublicKey (_cert);
-                                       }
-                                       catch (Exception e) {
-                                               string msg = Locale.GetText ("Unable to decode public key.");
-                                               throw new CryptographicException (msg, e);
-                                       }
-                               }
-                               return _publicKey;
-                       }
+                       get { return Impl.PublicKey; }
                } 
 
                public byte[] RawData {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               return base.GetRawCertData ();
-                       }
-               } 
+                       get { return GetRawCertData (); }
+               }
 
                public string SerialNumber {
-                       get { 
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               if (_serial == null) {
-                                       StringBuilder sb = new StringBuilder ();
-                                       byte[] serial = _cert.SerialNumber;
-                                       for (int i=serial.Length - 1; i >= 0; i--)
-                                               sb.Append (serial [i].ToString ("X2"));
-                                       _serial = sb.ToString ();
-                               }
-                               return _serial; 
-                       }
+                       get { return GetSerialNumberString (); }
                } 
 
                public Oid SignatureAlgorithm {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               if (signature_algorithm == null)
-                                       signature_algorithm = new Oid (_cert.SignatureAlgorithm);
-                               return signature_algorithm;
-                       }
+                       get { return Impl.SignatureAlgorithm; }
                } 
 
                public X500DistinguishedName SubjectName {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-
-                               if (subject_name == null)
-                                       subject_name = new X500DistinguishedName (_cert.GetSubjectName ().GetBytes ());
-                               return subject_name;
-                       }
+                       get { return Impl.SubjectName; }
                } 
 
                public string Thumbprint {
-                       get { return base.GetCertHashString (); }
+                       get { return GetCertHashString (); }
                } 
 
                public int Version {
-                       get {
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               return _cert.Version;
-                       }
+                       get { return Impl.Version; }
                }
 
                // methods
@@ -335,135 +215,7 @@ namespace System.Security.Cryptography.X509Certificates {
                [MonoTODO ("always return String.Empty for UpnName, DnsFromAlternativeName and UrlName")]
                public string GetNameInfo (X509NameType nameType, bool forIssuer) 
                {
-                       switch (nameType) {
-                       case X509NameType.SimpleName:
-                               if (_cert == null)
-                                       throw new CryptographicException (empty_error);
-                               // return CN= or, if missing, the first part of the DN
-                               ASN1 sn = forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ();
-                               ASN1 dn = Find (commonName, sn);
-                               if (dn != null)
-                                       return GetValueAsString (dn);
-                               if (sn.Count == 0)
-                                       return String.Empty;
-                               ASN1 last_entry = sn [sn.Count - 1];
-                               if (last_entry.Count == 0)
-                                       return String.Empty;
-                               return GetValueAsString (last_entry [0]);
-                       case X509NameType.EmailName:
-                               // return the E= part of the DN (if present)
-                               ASN1 e = Find (email, forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ());
-                               if (e != null)
-                                       return GetValueAsString (e);
-                               return String.Empty;
-                       case X509NameType.UpnName:
-                               // FIXME - must find/create test case
-                               return String.Empty;
-                       case X509NameType.DnsName:
-                               // return the CN= part of the DN (if present)
-                               ASN1 cn = Find (commonName, forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ());
-                               if (cn != null)
-                                       return GetValueAsString (cn);
-                               return String.Empty;
-                       case X509NameType.DnsFromAlternativeName:
-                               // FIXME - must find/create test case
-                               return String.Empty;
-                       case X509NameType.UrlName:
-                               // FIXME - must find/create test case
-                               return String.Empty;
-                       default:
-                               throw new ArgumentException ("nameType");
-                       }
-               }
-
-               static byte[] commonName = { 0x55, 0x04, 0x03 };
-               static byte[] email = { 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01 };
-
-               private ASN1 Find (byte[] oid, ASN1 dn)
-               {
-                       if (dn.Count == 0)
-                               return null;
-
-                       // process SET
-                       for (int i = 0; i < dn.Count; i++) {
-                               ASN1 set = dn [i];
-                               for (int j = 0; j < set.Count; j++) {
-                                       ASN1 pair = set [j];
-                                       if (pair.Count != 2)
-                                               continue;
-
-                                       ASN1 poid = pair [0];
-                                       if (poid == null)
-                                               continue;
-
-                                       if (poid.CompareValue (oid))
-                                               return pair;
-                               }
-                       }
-                       return null;
-               }
-
-               private string GetValueAsString (ASN1 pair)
-               {
-                       if (pair.Count != 2)
-                               return String.Empty;
-
-                       ASN1 value = pair [1];
-                       if ((value.Value == null) || (value.Length == 0))
-                               return String.Empty;
-
-                       if (value.Tag == 0x1E) {
-                               // BMPSTRING
-                               StringBuilder sb = new StringBuilder ();
-                               for (int j = 1; j < value.Value.Length; j += 2)
-                                       sb.Append ((char)value.Value [j]);
-                               return sb.ToString ();
-                       } else {
-                               return Encoding.UTF8.GetString (value.Value);
-                       }
-               }
-
-               private MX.X509Certificate ImportPkcs12 (byte[] rawData, string password)
-               {
-                       MX.PKCS12 pfx = null;
-                       if (string.IsNullOrEmpty (password)) {
-                               try {
-                                       // Support both unencrypted PKCS#12..
-                                       pfx = new MX.PKCS12 (rawData, (string)null);
-                               } catch {
-                                       // ..and PKCS#12 encrypted with an empty password
-                                       pfx = new MX.PKCS12 (rawData, string.Empty);
-                               }
-                       } else {
-                               pfx = new MX.PKCS12 (rawData, password);
-                       }
-
-                       if (pfx.Certificates.Count == 0) {
-                               // no certificate was found
-                               return null;
-                       } else if (pfx.Keys.Count == 0) {
-                               // no key were found - pick the first certificate
-                               return pfx.Certificates [0];
-                       } else {
-                               // find the certificate that match the first key
-                               MX.X509Certificate cert = null;
-                               var keypair = (pfx.Keys [0] as AsymmetricAlgorithm);
-                               string pubkey = keypair.ToXmlString (false);
-                               foreach (var c in pfx.Certificates) {
-                                       if (((c.RSA != null) && (pubkey == c.RSA.ToXmlString (false))) ||
-                                               ((c.DSA != null) && (pubkey == c.DSA.ToXmlString (false)))) {
-                                               cert = c;
-                                               break;
-                                       }
-                               }
-                               if (cert == null) {
-                                       cert = pfx.Certificates [0]; // no match, pick first certificate without keys
-                               } else {
-                                       cert.RSA = (keypair as RSA);
-                                       cert.DSA = (keypair as DSA);
-                               }
-                               return cert;
-                       }
+                       return Impl.GetNameInfo (nameType, forIssuer);
                }
 
                public override void Import (byte[] rawData) 
@@ -474,37 +226,8 @@ namespace System.Security.Cryptography.X509Certificates {
                [MonoTODO ("missing KeyStorageFlags support")]
                public override void Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
                {
-                       MX.X509Certificate cert = null;
-                       if (password == null) {
-                               try {
-                                       cert = new MX.X509Certificate (rawData);
-                               }
-                               catch (Exception e) {
-                                       try {
-                                               cert = ImportPkcs12 (rawData, null);
-                                       }
-                                       catch {
-                                               string msg = Locale.GetText ("Unable to decode certificate.");
-                                               // inner exception is the original (not second) exception
-                                               throw new CryptographicException (msg, e);
-                                       }
-                               }
-                       } else {
-                               // try PKCS#12
-                               try {
-                                       cert = ImportPkcs12 (rawData, password);
-                               }
-                               catch {
-                                       // it's possible to supply a (unrequired/unusued) password
-                                       // fix bug #79028
-                                       cert = new MX.X509Certificate (rawData);
-                               }
-                       }
-                       // we do not have to fully re-decode the certificate since X509Certificate does not deal with keys
-                       if (cert != null) {
-                               base.Import (cert.RawData, (string) null, keyStorageFlags);
-                               _cert = cert; // becuase base call will call Reset!
-                       }
+                       var impl = X509Helper2.Import (rawData, password, keyStorageFlags);
+                       ImportHandle (impl);
                }
 
                [MonoTODO ("SecureString is incomplete")]
@@ -536,64 +259,25 @@ namespace System.Security.Cryptography.X509Certificates {
                [MonoTODO ("X509ContentType.SerializedCert is not supported")]
                public override byte[] Export (X509ContentType contentType, string password)
                {
-                       if (_cert == null)
-                               throw new CryptographicException (empty_error);
-
-                       switch (contentType) {
-                       case X509ContentType.Cert:
-                               return _cert.RawData;
-                       case X509ContentType.Pfx: // this includes Pkcs12
-                               return ExportPkcs12 (password);
-                       case X509ContentType.SerializedCert:
-                               // TODO
-                               throw new NotSupportedException ();
-                       default:
-                               string msg = Locale.GetText ("This certificate format '{0}' cannot be exported.", contentType);
-                               throw new CryptographicException (msg);
-                       }
-               }
-
-               byte[] ExportPkcs12 (string password)
-               {
-                       var pfx = new MX.PKCS12 ();
-                       try {
-                               if (password != null)
-                                       pfx.Password = password;
-                               pfx.AddCertificate (_cert);
-                               var privateKey = PrivateKey;
-                               if (privateKey != null)
-                                       pfx.AddPkcs8ShroudedKeyBag (privateKey);
-                               return pfx.GetBytes ();
-                       } finally {
-                               pfx.Password = null;
-                       }
+                       return Impl.Export (contentType, password);
                }
 
                public override void Reset () 
                {
-                       _cert = null;
-                       _archived = false;
-                       _extensions = null;
-                       _name = String.Empty;
-                       _serial = null;
-                       _publicKey = null;
-                       issuer_name = null;
-                       subject_name = null;
-                       signature_algorithm = null;
+                       friendlyName = string.Empty;
                        base.Reset ();
                }
 
                public override string ToString ()
                {
-                       if (_cert == null)
+                       if (!IsValid)
                                return "System.Security.Cryptography.X509Certificates.X509Certificate2";
-
                        return base.ToString (true);
                }
 
                public override string ToString (bool verbose)
                {
-                       if (_cert == null)
+                       if (!IsValid)
                                return "System.Security.Cryptography.X509Certificates.X509Certificate2";
 
                        // the non-verbose X509Certificate2 == verbose X509Certificate
@@ -643,14 +327,7 @@ namespace System.Security.Cryptography.X509Certificates {
                [MonoTODO ("by default this depends on the incomplete X509Chain")]
                public bool Verify ()
                {
-                       if (_cert == null)
-                               throw new CryptographicException (empty_error);
-
-                       X509Chain chain = X509Chain.Create ();
-                       if (!chain.Build (this))
-                               return false;
-                       // TODO - check chain and other stuff ???
-                       return true;
+                       return Impl.Verify (this);
                }
 
                // static methods
@@ -717,8 +394,14 @@ namespace System.Security.Cryptography.X509Certificates {
                // internal stuff because X509Certificate2 isn't complete enough
                // (maybe X509Certificate3 will be better?)
 
+               [Obsolete ("KILL")]
                internal MX.X509Certificate MonoCertificate {
-                       get { return _cert; }
+                       get {
+                               var monoImpl = Impl as X509Certificate2ImplMono;
+                               if (monoImpl == null)
+                                       throw new NotSupportedException ();
+                               return monoImpl.MonoCertificate;
+                       }
                }
 
 #else
diff --git a/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2Impl.cs b/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2Impl.cs
new file mode 100644 (file)
index 0000000..60e256a
--- /dev/null
@@ -0,0 +1,82 @@
+//
+// X509Certificate2Impl.cs
+//
+// Authors:
+//     Martin Baulig  <martin.baulig@xamarin.com>
+//
+// Copyright (C) 2016 Xamarin, Inc. (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+namespace System.Security.Cryptography.X509Certificates
+{
+       internal abstract class X509Certificate2Impl : X509CertificateImpl
+       {
+#if SECURITY_DEP
+
+               public abstract bool Archived {
+                       get; set;
+               }
+
+               public abstract X509ExtensionCollection Extensions {
+                       get;
+               }
+
+               public abstract bool HasPrivateKey {
+                       get;
+               }
+
+               public abstract X500DistinguishedName IssuerName {
+                       get;
+               }
+
+               public abstract AsymmetricAlgorithm PrivateKey {
+                       get; set;
+               }
+
+               public abstract PublicKey PublicKey {
+                       get;
+               }
+
+               public abstract Oid SignatureAlgorithm {
+                       get;
+               }
+
+               public abstract X500DistinguishedName SubjectName {
+                       get;
+               }
+
+               public abstract int Version {
+                       get;
+               }
+
+               public abstract string GetNameInfo (X509NameType nameType, bool forIssuer);
+
+               public abstract void Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags);
+
+               public abstract byte[] Export (X509ContentType contentType, string password);
+
+               public abstract bool Verify (X509Certificate2 thisCertificate);
+
+               public abstract void Reset ();
+
+#endif
+       }
+}
diff --git a/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2ImplMono.cs b/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Certificate2ImplMono.cs
new file mode 100644 (file)
index 0000000..bfb2696
--- /dev/null
@@ -0,0 +1,699 @@
+//
+// X509Certificate2ImplMono
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//     Martin Baulig  <martin.baulig@xamarin.com>
+//
+// (C) 2003 Motus Technologies Inc. (http://www.motus.com)
+// Copyright (C) 2004-2006 Novell Inc. (http://www.novell.com)
+// Copyright (C) 2015-2016 Xamarin, Inc. (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+#if SECURITY_DEP
+
+#if MONO_SECURITY_ALIAS
+extern alias MonoSecurity;
+using MonoSecurity::Mono.Security;
+using MonoSecurity::Mono.Security.Cryptography;
+using MX = MonoSecurity::Mono.Security.X509;
+#else
+using Mono.Security;
+using Mono.Security.Cryptography;
+using MX = Mono.Security.X509;
+#endif
+
+using System.IO;
+using System.Text;
+using System.Collections;
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       internal class X509Certificate2ImplMono : X509Certificate2Impl
+       {
+               bool _archived;
+               X509ExtensionCollection _extensions;
+               string _serial;
+               PublicKey _publicKey;
+               X500DistinguishedName issuer_name;
+               X500DistinguishedName subject_name;
+               Oid signature_algorithm;
+
+               MX.X509Certificate _cert;
+
+               static string empty_error = Locale.GetText ("Certificate instance is empty.");
+
+               public override bool IsValid {
+                       get {
+                               return _cert != null;
+                       }
+               }
+
+               public override IntPtr Handle {
+                       get { return IntPtr.Zero; }
+               }
+
+               public override IntPtr GetNativeAppleCertificate ()
+               {
+                       return IntPtr.Zero;
+               }
+
+               internal X509Certificate2ImplMono (MX.X509Certificate cert)
+               {
+                       this._cert = cert;
+               }
+
+               public override X509CertificateImpl Clone ()
+               {
+                       ThrowIfContextInvalid ();
+                       return new X509Certificate2ImplMono (_cert);
+               }
+
+               #region Implemented X509CertificateImpl members
+
+               public override string GetIssuerName (bool legacyV1Mode)
+               {
+                       ThrowIfContextInvalid ();
+                       if (legacyV1Mode)
+                               return _cert.IssuerName;
+                       else
+                               return MX.X501.ToString (_cert.GetIssuerName (), true, ", ", true);
+               }
+
+               public override string GetSubjectName (bool legacyV1Mode)
+               {
+                       ThrowIfContextInvalid ();
+                       if (legacyV1Mode)
+                               return _cert.SubjectName;
+                       else
+                               return MX.X501.ToString (_cert.GetSubjectName (), true, ", ", true);
+               }
+
+               public override byte[] GetRawCertData ()
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.RawData;
+               }
+
+               protected override byte[] GetCertHash (bool lazy)
+               {
+                       ThrowIfContextInvalid ();
+                       SHA1 sha = SHA1.Create ();
+                       return sha.ComputeHash (_cert.RawData);
+               }
+
+               public override DateTime GetValidFrom ()
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.ValidFrom;
+               }
+
+               public override DateTime GetValidUntil ()
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.ValidUntil;
+               }
+
+               public override bool Equals (X509CertificateImpl other, out bool result)
+               {
+                       // Use default implementation
+                       result = false;
+                       return false;
+               }
+
+               public override string GetKeyAlgorithm () 
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.KeyAlgorithm;
+               }
+
+               public override byte[] GetKeyAlgorithmParameters () 
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.KeyAlgorithmParameters;
+               }
+
+               public override byte[] GetPublicKey ()
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.PublicKey;
+               }
+
+               public override byte[] GetSerialNumber ()
+               {
+                       ThrowIfContextInvalid ();
+                       return _cert.SerialNumber;
+               }
+
+               public override byte[] Export (X509ContentType contentType, byte[] password)
+               {
+                       ThrowIfContextInvalid ();
+
+                       switch (contentType) {
+                       case X509ContentType.Cert:
+                               return GetRawCertData ();
+                       case X509ContentType.Pfx: // this includes Pkcs12
+                               // TODO
+                               throw new NotSupportedException ();
+                       case X509ContentType.SerializedCert:
+                               // TODO
+                               throw new NotSupportedException ();
+                       default:
+                               string msg = Locale.GetText ("This certificate format '{0}' cannot be exported.", contentType);
+                               throw new CryptographicException (msg);
+                       }
+               }
+
+               #endregion
+
+               // constructors
+
+               public X509Certificate2ImplMono ()
+               {
+                       _cert = null;
+               }
+
+               // properties
+
+               public override bool Archived {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               return _archived;
+                       }
+                       set {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               _archived = value;
+                       }
+               }
+
+               public override X509ExtensionCollection Extensions {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               if (_extensions == null)
+                                       _extensions = new X509ExtensionCollection (_cert);
+                               return _extensions;
+                       }
+               }
+
+               // FIXME - Could be more efficient
+               public override bool HasPrivateKey {
+                       get { return PrivateKey != null; }
+               }
+
+               public override X500DistinguishedName IssuerName {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               if (issuer_name == null)
+                                       issuer_name = new X500DistinguishedName (_cert.GetIssuerName ().GetBytes ());
+                               return issuer_name;
+                       }
+               } 
+
+               public override AsymmetricAlgorithm PrivateKey {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               try {
+                                       if (_cert.RSA != null) {
+                                               RSACryptoServiceProvider rcsp = _cert.RSA as RSACryptoServiceProvider;
+                                               if (rcsp != null)
+                                                       return rcsp.PublicOnly ? null : rcsp;
+
+                                               RSAManaged rsam = _cert.RSA as RSAManaged;
+                                               if (rsam != null)
+                                                       return rsam.PublicOnly ? null : rsam;
+
+                                               _cert.RSA.ExportParameters (true);
+                                               return _cert.RSA;
+                                       } else if (_cert.DSA != null) {
+                                               DSACryptoServiceProvider dcsp = _cert.DSA as DSACryptoServiceProvider;
+                                               if (dcsp != null)
+                                                       return dcsp.PublicOnly ? null : dcsp;
+
+                                               _cert.DSA.ExportParameters (true);
+                                               return _cert.DSA;
+                                       }
+                               }
+                               catch {
+                               }
+                               return null;
+                       }
+                       set {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+
+                               // allow NULL so we can "forget" the key associated to the certificate
+                               // e.g. in case we want to export it in another format (see bug #396620)
+                               if (value == null) {
+                                       _cert.RSA = null;
+                                       _cert.DSA = null;
+                               } else  if (value is RSA)
+                                       _cert.RSA = (RSA) value;
+                               else if (value is DSA)
+                                       _cert.DSA = (DSA) value;
+                               else
+                                       throw new NotSupportedException ();
+                       }
+               } 
+
+               public override PublicKey PublicKey {
+                       get { 
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+
+                               if (_publicKey == null) {
+                                       try {
+                                               _publicKey = new PublicKey (_cert);
+                                       }
+                                       catch (Exception e) {
+                                               string msg = Locale.GetText ("Unable to decode public key.");
+                                               throw new CryptographicException (msg, e);
+                                       }
+                               }
+                               return _publicKey;
+                       }
+               }
+
+               public override Oid SignatureAlgorithm {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+
+                               if (signature_algorithm == null)
+                                       signature_algorithm = new Oid (_cert.SignatureAlgorithm);
+                               return signature_algorithm;
+                       }
+               } 
+
+               public override X500DistinguishedName SubjectName {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+
+                               if (subject_name == null)
+                                       subject_name = new X500DistinguishedName (_cert.GetSubjectName ().GetBytes ());
+                               return subject_name;
+                       }
+               } 
+
+               public override int Version {
+                       get {
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               return _cert.Version;
+                       }
+               }
+
+               // methods
+
+               [MonoTODO ("always return String.Empty for UpnName, DnsFromAlternativeName and UrlName")]
+               public override string GetNameInfo (X509NameType nameType, bool forIssuer) 
+               {
+                       switch (nameType) {
+                       case X509NameType.SimpleName:
+                               if (_cert == null)
+                                       throw new CryptographicException (empty_error);
+                               // return CN= or, if missing, the first part of the DN
+                               ASN1 sn = forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ();
+                               ASN1 dn = Find (commonName, sn);
+                               if (dn != null)
+                                       return GetValueAsString (dn);
+                               if (sn.Count == 0)
+                                       return String.Empty;
+                               ASN1 last_entry = sn [sn.Count - 1];
+                               if (last_entry.Count == 0)
+                                       return String.Empty;
+                               return GetValueAsString (last_entry [0]);
+                       case X509NameType.EmailName:
+                               // return the E= part of the DN (if present)
+                               ASN1 e = Find (email, forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ());
+                               if (e != null)
+                                       return GetValueAsString (e);
+                               return String.Empty;
+                       case X509NameType.UpnName:
+                               // FIXME - must find/create test case
+                               return String.Empty;
+                       case X509NameType.DnsName:
+                               // return the CN= part of the DN (if present)
+                               ASN1 cn = Find (commonName, forIssuer ? _cert.GetIssuerName () : _cert.GetSubjectName ());
+                               if (cn != null)
+                                       return GetValueAsString (cn);
+                               return String.Empty;
+                       case X509NameType.DnsFromAlternativeName:
+                               // FIXME - must find/create test case
+                               return String.Empty;
+                       case X509NameType.UrlName:
+                               // FIXME - must find/create test case
+                               return String.Empty;
+                       default:
+                               throw new ArgumentException ("nameType");
+                       }
+               }
+
+               static byte[] commonName = { 0x55, 0x04, 0x03 };
+               static byte[] email = { 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x09, 0x01 };
+
+               private ASN1 Find (byte[] oid, ASN1 dn)
+               {
+                       if (dn.Count == 0)
+                               return null;
+
+                       // process SET
+                       for (int i = 0; i < dn.Count; i++) {
+                               ASN1 set = dn [i];
+                               for (int j = 0; j < set.Count; j++) {
+                                       ASN1 pair = set [j];
+                                       if (pair.Count != 2)
+                                               continue;
+
+                                       ASN1 poid = pair [0];
+                                       if (poid == null)
+                                               continue;
+
+                                       if (poid.CompareValue (oid))
+                                               return pair;
+                               }
+                       }
+                       return null;
+               }
+
+               private string GetValueAsString (ASN1 pair)
+               {
+                       if (pair.Count != 2)
+                               return String.Empty;
+
+                       ASN1 value = pair [1];
+                       if ((value.Value == null) || (value.Length == 0))
+                               return String.Empty;
+
+                       if (value.Tag == 0x1E) {
+                               // BMPSTRING
+                               StringBuilder sb = new StringBuilder ();
+                               for (int j = 1; j < value.Value.Length; j += 2)
+                                       sb.Append ((char)value.Value [j]);
+                               return sb.ToString ();
+                       } else {
+                               return Encoding.UTF8.GetString (value.Value);
+                       }
+               }
+
+               private MX.X509Certificate ImportPkcs12 (byte[] rawData, string password)
+               {
+                       MX.PKCS12 pfx = null;
+                       if (string.IsNullOrEmpty (password)) {
+                               try {
+                                       // Support both unencrypted PKCS#12..
+                                       pfx = new MX.PKCS12 (rawData, (string)null);
+                               } catch {
+                                       // ..and PKCS#12 encrypted with an empty password
+                                       pfx = new MX.PKCS12 (rawData, string.Empty);
+                               }
+                       } else {
+                               pfx = new MX.PKCS12 (rawData, password);
+                       }
+
+                       if (pfx.Certificates.Count == 0) {
+                               // no certificate was found
+                               return null;
+                       } else if (pfx.Keys.Count == 0) {
+                               // no key were found - pick the first certificate
+                               return pfx.Certificates [0];
+                       } else {
+                               // find the certificate that match the first key
+                               MX.X509Certificate cert = null;
+                               var keypair = (pfx.Keys [0] as AsymmetricAlgorithm);
+                               string pubkey = keypair.ToXmlString (false);
+                               foreach (var c in pfx.Certificates) {
+                                       if (((c.RSA != null) && (pubkey == c.RSA.ToXmlString (false))) ||
+                                               ((c.DSA != null) && (pubkey == c.DSA.ToXmlString (false)))) {
+                                               cert = c;
+                                               break;
+                                       }
+                               }
+                               if (cert == null) {
+                                       cert = pfx.Certificates [0]; // no match, pick first certificate without keys
+                               } else {
+                                       cert.RSA = (keypair as RSA);
+                                       cert.DSA = (keypair as DSA);
+                               }
+                               return cert;
+                       }
+               }
+
+               [MonoTODO ("missing KeyStorageFlags support")]
+               public override void Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
+               {
+                       MX.X509Certificate cert = null;
+                       if (password == null) {
+                               try {
+                                       cert = new MX.X509Certificate (rawData);
+                               }
+                               catch (Exception e) {
+                                       try {
+                                               cert = ImportPkcs12 (rawData, null);
+                                       }
+                                       catch {
+                                               string msg = Locale.GetText ("Unable to decode certificate.");
+                                               // inner exception is the original (not second) exception
+                                               throw new CryptographicException (msg, e);
+                                       }
+                               }
+                       } else {
+                               // try PKCS#12
+                               try {
+                                       cert = ImportPkcs12 (rawData, password);
+                               }
+                               catch {
+                                       // it's possible to supply a (unrequired/unusued) password
+                                       // fix bug #79028
+                                       cert = new MX.X509Certificate (rawData);
+                               }
+                       }
+                       _cert = cert;
+               }
+
+               [MonoTODO ("X509ContentType.SerializedCert is not supported")]
+               public override byte[] Export (X509ContentType contentType, string password)
+               {
+                       if (_cert == null)
+                               throw new CryptographicException (empty_error);
+
+                       switch (contentType) {
+                       case X509ContentType.Cert:
+                               return _cert.RawData;
+                       case X509ContentType.Pfx: // this includes Pkcs12
+                               return ExportPkcs12 (password);
+                       case X509ContentType.SerializedCert:
+                               // TODO
+                               throw new NotSupportedException ();
+                       default:
+                               string msg = Locale.GetText ("This certificate format '{0}' cannot be exported.", contentType);
+                               throw new CryptographicException (msg);
+                       }
+               }
+
+               byte[] ExportPkcs12 (string password)
+               {
+                       var pfx = new MX.PKCS12 ();
+                       try {
+                               var attrs = new Hashtable ();
+                               var localKeyId = new ArrayList ();
+                               localKeyId.Add (new byte[] { 1, 0, 0, 0 });
+                               attrs.Add (MX.PKCS9.localKeyId, localKeyId);
+
+                               if (password != null)
+                                       pfx.Password = password;
+                               pfx.AddCertificate (_cert, attrs);
+                               var privateKey = PrivateKey;
+                               if (privateKey != null)
+                                       pfx.AddPkcs8ShroudedKeyBag (privateKey, attrs);
+                               return pfx.GetBytes ();
+                       } finally {
+                               pfx.Password = null;
+                       }
+               }
+
+               public override void Reset () 
+               {
+                       _cert = null;
+                       _archived = false;
+                       _extensions = null;
+                       _serial = null;
+                       _publicKey = null;
+                       issuer_name = null;
+                       subject_name = null;
+                       signature_algorithm = null;
+               }
+
+               public override string ToString ()
+               {
+                       if (_cert == null)
+                               return "System.Security.Cryptography.X509Certificates.X509Certificate2";
+
+                       return ToString (true);
+               }
+
+               public override string ToString (bool verbose)
+               {
+                       if (_cert == null)
+                               return "System.Security.Cryptography.X509Certificates.X509Certificate2";
+
+                       string nl = Environment.NewLine;
+                       StringBuilder sb = new StringBuilder ();
+
+                       // the non-verbose X509Certificate2 == verbose X509Certificate
+                       if (!verbose) {
+                               sb.AppendFormat ("[Subject]{0}  {1}{0}{0}", nl, GetSubjectName (false));
+                               sb.AppendFormat ("[Issuer]{0}  {1}{0}{0}", nl, GetIssuerName (false));
+                               sb.AppendFormat ("[Not Before]{0}  {1}{0}{0}", nl, GetValidFrom ().ToLocalTime ());
+                               sb.AppendFormat ("[Not After]{0}  {1}{0}{0}", nl, GetValidUntil ().ToLocalTime ());
+                               sb.AppendFormat ("[Thumbprint]{0}  {1}{0}", nl, X509Helper.ToHexString (GetCertHash ()));
+                               sb.Append (nl);
+                               return sb.ToString ();
+                       }
+
+                       sb.AppendFormat ("[Version]{0}  V{1}{0}{0}", nl, Version);
+                       sb.AppendFormat ("[Subject]{0}  {1}{0}{0}", nl, GetSubjectName (false));
+                       sb.AppendFormat ("[Issuer]{0}  {1}{0}{0}", nl, GetIssuerName (false));
+                       sb.AppendFormat ("[Serial Number]{0}  {1}{0}{0}", nl, GetSerialNumber ());
+                       sb.AppendFormat ("[Not Before]{0}  {1}{0}{0}", nl, GetValidFrom ().ToLocalTime ());
+                       sb.AppendFormat ("[Not After]{0}  {1}{0}{0}", nl, GetValidUntil ().ToLocalTime ());
+                       sb.AppendFormat ("[Thumbprint]{0}  {1}{0}", nl, X509Helper.ToHexString (GetCertHash ()));
+                       sb.AppendFormat ("[Signature Algorithm]{0}  {1}({2}){0}{0}", nl, SignatureAlgorithm.FriendlyName, 
+                               SignatureAlgorithm.Value);
+
+                       AsymmetricAlgorithm key = PublicKey.Key;
+                       sb.AppendFormat ("[Public Key]{0}  Algorithm: ", nl);
+                       if (key is RSA)
+                               sb.Append ("RSA");
+                       else if (key is DSA)
+                               sb.Append ("DSA");
+                       else
+                               sb.Append (key.ToString ());
+                       sb.AppendFormat ("{0}  Length: {1}{0}  Key Blob: ", nl, key.KeySize);
+                       AppendBuffer (sb, PublicKey.EncodedKeyValue.RawData);
+                       sb.AppendFormat ("{0}  Parameters: ", nl);
+                       AppendBuffer (sb, PublicKey.EncodedParameters.RawData);
+                       sb.Append (nl);
+
+                       return sb.ToString ();
+               }
+
+               private static void AppendBuffer (StringBuilder sb, byte[] buffer)
+               {
+                       if (buffer == null)
+                               return;
+                       for (int i=0; i < buffer.Length; i++) {
+                               sb.Append (buffer [i].ToString ("x2"));
+                               if (i < buffer.Length - 1)
+                                       sb.Append (" ");
+                       }
+               }
+
+               [MonoTODO ("by default this depends on the incomplete X509Chain")]
+               public override bool Verify (X509Certificate2 thisCertificate)
+               {
+                       if (_cert == null)
+                               throw new CryptographicException (empty_error);
+
+                       X509Chain chain = X509Chain.Create ();
+                       if (!chain.Build (thisCertificate))
+                               return false;
+                       // TODO - check chain and other stuff ???
+                       return true;
+               }
+
+               // static methods
+
+               private static byte[] signedData = new byte[] { 0x2a, 0x86, 0x48, 0x86, 0xf7, 0x0d, 0x01, 0x07, 0x02 };
+
+               [MonoTODO ("Detection limited to Cert, Pfx, Pkcs12, Pkcs7 and Unknown")]
+               public static X509ContentType GetCertContentType (byte[] rawData)
+               {
+                       if ((rawData == null) || (rawData.Length == 0))
+                               throw new ArgumentException ("rawData");
+
+                       X509ContentType type = X509ContentType.Unknown;
+                       try {
+                               ASN1 data = new ASN1 (rawData);
+                               if (data.Tag != 0x30) {
+                                       string msg = Locale.GetText ("Unable to decode certificate.");
+                                       throw new CryptographicException (msg);
+                               }
+
+                               if (data.Count == 0)
+                                       return type;
+
+                               if (data.Count == 3) {
+                                       switch (data [0].Tag) {
+                                       case 0x30:
+                                               // SEQUENCE / SEQUENCE / BITSTRING
+                                               if ((data [1].Tag == 0x30) && (data [2].Tag == 0x03))
+                                                       type = X509ContentType.Cert;
+                                               break;
+                                       case 0x02:
+                                               // INTEGER / SEQUENCE / SEQUENCE
+                                               if ((data [1].Tag == 0x30) && (data [2].Tag == 0x30))
+                                                       type = X509ContentType.Pkcs12;
+                                               // note: Pfx == Pkcs12
+                                               break;
+                                       }
+                               }
+                               // check for PKCS#7 (count unknown but greater than 0)
+                               // SEQUENCE / OID (signedData)
+                               if ((data [0].Tag == 0x06) && data [0].CompareValue (signedData))
+                                       type = X509ContentType.Pkcs7;
+                       }
+                       catch (Exception e) {
+                               string msg = Locale.GetText ("Unable to decode certificate.");
+                               throw new CryptographicException (msg, e);
+                       }
+
+                       return type;
+               }
+
+               [MonoTODO ("Detection limited to Cert, Pfx, Pkcs12 and Unknown")]
+               public static X509ContentType GetCertContentType (string fileName)
+               {
+                       if (fileName == null)
+                               throw new ArgumentNullException ("fileName");
+                       if (fileName.Length == 0)
+                               throw new ArgumentException ("fileName");
+
+                       byte[] data = File.ReadAllBytes (fileName);
+                       return GetCertContentType (data);
+               }
+
+               // internal stuff because X509Certificate2 isn't complete enough
+               // (maybe X509Certificate3 will be better?)
+
+               internal MX.X509Certificate MonoCertificate {
+                       get { return _cert; }
+               }
+       }
+}
+
+#endif
index 9910f3982705c9187eb3a6e9415a507cd9b3e61a..a7c24d385f8fe38d227f6609085127b4bf604c6a 100644 (file)
@@ -42,23 +42,27 @@ using System.Text;
 
 namespace System.Security.Cryptography.X509Certificates {
 
-       public class X509Chain {
+       public class X509Chain : IDisposable {
 
-               private StoreLocation location;
-               private X509ChainElementCollection elements;
-               private X509ChainPolicy policy;
-               private X509ChainStatus[] status;
+               X509ChainImpl impl;
 
                static X509ChainStatus[] Empty = new X509ChainStatus [0];
 
-               // RFC3280 variables
-               private int max_path_length;
-               private X500DistinguishedName working_issuer_name;
-//             private string working_public_key_algorithm;
-               private AsymmetricAlgorithm working_public_key;
+               internal X509ChainImpl Impl {
+                       get {
+                               X509Helper2.ThrowIfContextInvalid (impl);
+                               return impl;
+                       }
+               }
 
-               // other flags
-               private X509ChainElement bce_restriction;
+               internal bool IsValid {
+                       get { return X509Helper2.IsValid (impl); }
+               }
+
+               internal void ThrowIfContextInvalid ()
+               {
+                       X509Helper2.ThrowIfContextInvalid (impl);
+               }
 
                // constructors
 
@@ -69,9 +73,13 @@ namespace System.Security.Cryptography.X509Certificates {
 
                public X509Chain (bool useMachineContext) 
                {
-                       location = useMachineContext ? StoreLocation.LocalMachine : StoreLocation.CurrentUser;
-                       elements = new X509ChainElementCollection ();
-                       policy = new X509ChainPolicy ();
+                       impl = X509Helper2.CreateChainImpl (useMachineContext);
+               }
+
+               internal X509Chain (X509ChainImpl impl)
+               {
+                       X509Helper2.ThrowIfContextInvalid (impl);
+                       this.impl = impl;
                }
 
                [MonoTODO ("Mono's X509Chain is fully managed. All handles are invalid.")]
@@ -85,153 +93,37 @@ namespace System.Security.Cryptography.X509Certificates {
 
                [MonoTODO ("Mono's X509Chain is fully managed. Always returns IntPtr.Zero.")]
                public IntPtr ChainContext {
-                       get { return IntPtr.Zero; }
+                       get {
+                               if (impl != null && impl.IsValid)
+                                       return impl.Handle;
+                               return IntPtr.Zero;
+                       }
                }
 
                public X509ChainElementCollection ChainElements {
-                       get { return elements; }
+                       get { return Impl.ChainElements; }
                }
 
                public X509ChainPolicy ChainPolicy {
-                       get { return policy; }
-                       set { policy = value; }
+                       get { return Impl.ChainPolicy; }
+                       set { Impl.ChainPolicy = value; }
                }
 
                public X509ChainStatus[] ChainStatus {
-                       get { 
-                               if (status == null)
-                                       return Empty;
-                               return status;
-                       }
-               } 
+                       get { return Impl.ChainStatus; }
+               }
 
                // methods
 
                [MonoTODO ("Not totally RFC3280 compliant, but neither is MS implementation...")]
                public bool Build (X509Certificate2 certificate)
                {
-                       if (certificate == null)
-                               throw new ArgumentException ("certificate");
-
-                       Reset ();
-                       X509ChainStatusFlags flag;
-                       try {
-                               flag = BuildChainFrom (certificate);
-                               ValidateChain (flag);
-                       }
-                       catch (CryptographicException ce) {
-                               throw new ArgumentException ("certificate", ce);
-                       }
-
-                       X509ChainStatusFlags total = X509ChainStatusFlags.NoError;
-                       ArrayList list = new ArrayList ();
-                       // build "global" ChainStatus from the ChainStatus of every ChainElements
-                       foreach (X509ChainElement ce in elements) {
-                               foreach (X509ChainStatus cs in ce.ChainElementStatus) {
-                                       // we MUST avoid duplicates in the "global" list
-                                       if ((total & cs.Status) != cs.Status) {
-                                               list.Add (cs);
-                                               total |= cs.Status;
-                                       }
-                               }
-                       }
-                       // and if required add some
-                       if (flag != X509ChainStatusFlags.NoError) {
-                               list.Insert (0, new X509ChainStatus (flag));
-                       }
-                       status = (X509ChainStatus[]) list.ToArray (typeof (X509ChainStatus));
-
-                       // (fast path) this ignore everything we have checked
-                       if ((status.Length == 0) || (ChainPolicy.VerificationFlags == X509VerificationFlags.AllFlags))
-                               return true;
-
-                       bool result = true;
-                       // now check if exclude some verification for the "end result" (boolean)
-                       foreach (X509ChainStatus cs in status) {
-                               switch (cs.Status) {
-                               case X509ChainStatusFlags.UntrustedRoot:
-                               case X509ChainStatusFlags.PartialChain:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.AllowUnknownCertificateAuthority) != 0);
-                                       break;
-                               case X509ChainStatusFlags.NotTimeValid:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreNotTimeValid) != 0);
-                                       break;
-                               // FIXME - from here we needs new test cases for all cases
-                               case X509ChainStatusFlags.NotTimeNested:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreNotTimeNested) != 0);
-                                       break;
-                               case X509ChainStatusFlags.InvalidBasicConstraints:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidBasicConstraints) != 0);
-                                       break;
-                               case X509ChainStatusFlags.InvalidPolicyConstraints:
-                               case X509ChainStatusFlags.NoIssuanceChainPolicy:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidPolicy) != 0);
-                                       break;
-                               case X509ChainStatusFlags.InvalidNameConstraints:
-                               case X509ChainStatusFlags.HasNotSupportedNameConstraint:
-                               case X509ChainStatusFlags.HasNotPermittedNameConstraint:
-                               case X509ChainStatusFlags.HasExcludedNameConstraint:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidName) != 0);
-                                       break;
-                               case X509ChainStatusFlags.InvalidExtension:
-                                       // not sure ?!?
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreWrongUsage) != 0);
-                                       break;
-                               //
-                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreRootRevocationUnknown) != 0)
-                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreEndRevocationUnknown) != 0)
-                               case X509ChainStatusFlags.CtlNotTimeValid:
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreCtlNotTimeValid) != 0);
-                                       break;
-                               case X509ChainStatusFlags.CtlNotSignatureValid:
-                                       // ?
-                                       break;
-                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreCtlSignerRevocationUnknown) != 0);
-                               case X509ChainStatusFlags.CtlNotValidForUsage:
-                                       // FIXME - does IgnoreWrongUsage apply to CTL (it doesn't have Ctl in it's name like the others)
-                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreWrongUsage) != 0);
-                                       break;
-                               default:
-                                       result = false;
-                                       break;
-                               }
-                               // once we have one failure there's no need to check further
-                               if (!result)
-                                       return false;
-                       }
-
-                       // every "problem" was excluded
-                       return true;
+                       return Impl.Build (certificate);
                }
 
                public void Reset () 
                {
-                       // note: this call doesn't Reset the X509ChainPolicy
-                       if ((status != null) && (status.Length != 0))
-                               status = null;
-                       if (elements.Count > 0)
-                               elements.Clear ();
-                       if (user_root_store != null) {
-                               user_root_store.Close ();
-                               user_root_store = null;
-                       }
-                       if (root_store != null) {
-                               root_store.Close ();
-                               root_store = null;
-                       }
-                       if (user_ca_store != null) {
-                               user_ca_store.Close ();
-                               user_ca_store = null;
-                       }
-                       if (ca_store != null) {
-                               ca_store.Close ();
-                               ca_store = null;
-                       }
-                       roots = null;
-                       cas = null;
-                       collection = null;
-                       bce_restriction = null;
-                       working_public_key = null;
+                       Impl.Reset ();
                }
 
                // static methods
@@ -245,717 +137,23 @@ namespace System.Security.Cryptography.X509Certificates {
 #endif
                }
 
-               // private stuff
-
-               private X509Certificate2Collection roots;
-               private X509Certificate2Collection cas;
-               private X509Store root_store;
-               private X509Store ca_store;
-               private X509Store user_root_store;
-               private X509Store user_ca_store;
-
-               private X509Certificate2Collection Roots {
-                       get {
-                               if (roots == null) {
-                                       X509Certificate2Collection c = new X509Certificate2Collection ();
-                                       X509Store store = LMRootStore;
-                                       if (location == StoreLocation.CurrentUser)
-                                               c.AddRange (UserRootStore.Certificates);
-                                       c.AddRange (store.Certificates);
-                                       roots = c;
-                               }
-                               return roots;
-                       }
-               }
-
-               private X509Certificate2Collection CertificateAuthorities {
-                       get {
-                               if (cas == null) {
-                                       X509Certificate2Collection c = new X509Certificate2Collection ();
-                                       X509Store store = LMCAStore;
-                                       if (location == StoreLocation.CurrentUser)
-                                               c.AddRange (UserCAStore.Certificates);
-                                       c.AddRange (store.Certificates);
-                                       cas = c;
-                               }
-                               return cas;
-                       }
-               }
-
-               private X509Store LMRootStore {
-                       get {
-                               if (root_store == null) {
-                                       root_store = new X509Store (StoreName.Root, StoreLocation.LocalMachine);
-                                       try {
-                                               root_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
-                                       } catch {
-                                       }
-                               }
-                               return root_store;
-                       }
-               }
-
-               private X509Store UserRootStore {
-                       get {
-                               if (user_root_store == null) {
-                                       user_root_store = new X509Store (StoreName.Root, StoreLocation.CurrentUser);
-                                       try {
-                                               user_root_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
-                                       } catch {
-                                       }
-                               }
-                               return user_root_store;
-                       }
-               }
-
-               private X509Store LMCAStore {
-                       get {
-                               if (ca_store == null) {
-                                       ca_store = new X509Store (StoreName.CertificateAuthority, StoreLocation.LocalMachine);
-                                       try {
-                                               ca_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
-                                       } catch {
-                                       }
-                               }
-                               return ca_store;
-                       }
-               }
-
-               private X509Store UserCAStore {
-                       get {
-                               if (user_ca_store == null) {
-                                       user_ca_store = new X509Store (StoreName.CertificateAuthority, StoreLocation.CurrentUser);
-                                       try {
-                                               user_ca_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
-                                       } catch {
-                                       }
-                               }
-                               return user_ca_store;
-                       }
-               }
-               // *** certificate chain/path building stuff ***
-
-               private X509Certificate2Collection collection;
-
-               // we search local user (default) or machine certificate store 
-               // and in the extra certificate supplied in ChainPolicy.ExtraStore
-               private X509Certificate2Collection CertificateCollection {
-                       get {
-                               if (collection == null) {
-                                       collection = new X509Certificate2Collection (ChainPolicy.ExtraStore);
-                                       collection.AddRange (Roots);
-                                       collection.AddRange (CertificateAuthorities);
-                               }
-                               return collection;
-                       }
-               }
-
-               // This is a non-recursive chain/path building algorithm. 
-               //
-               // At this stage we only checks for PartialChain, Cyclic and UntrustedRoot errors are they
-               // affect the path building (other errors are verification errors).
-               //
-               // Note that the order match the one we need to match MS and not the one defined in RFC3280,
-               // we also include the trusted root certificate (trust anchor in RFC3280) in the list.
-               // (this isn't an issue, just keep that in mind if you look at the source and the RFC)
-               private X509ChainStatusFlags BuildChainFrom (X509Certificate2 certificate)
-               {
-                       elements.Add (certificate);
-
-                       while (!IsChainComplete (certificate)) {
-                               certificate = FindParent (certificate);
-
-                               if (certificate == null)
-                                       return X509ChainStatusFlags.PartialChain;
-
-                               if (elements.Contains (certificate))
-                                       return X509ChainStatusFlags.Cyclic;
-
-                               elements.Add (certificate);
-                       }
-
-                       // roots may be supplied (e.g. in the ExtraStore) so we need to confirm their
-                       // trustiness (what a cute word) in the trusted root collection
-                       if (!Roots.Contains (certificate))
-                               elements [elements.Count - 1].StatusFlags |= X509ChainStatusFlags.UntrustedRoot;
-
-                       return X509ChainStatusFlags.NoError;
-               }
-
-
-               private X509Certificate2 SelectBestFromCollection (X509Certificate2 child, X509Certificate2Collection c)
-               {
-                       switch (c.Count) {
-                       case 0:
-                               return null;
-                       case 1:
-                               return c [0];
-                       default:
-                               // multiple candidate, keep only the ones that are still valid
-                               X509Certificate2Collection time_valid = c.Find (X509FindType.FindByTimeValid, ChainPolicy.VerificationTime, false);
-                               switch (time_valid.Count) {
-                               case 0:
-                                       // that's too restrictive, let's revert and try another thing...
-                                       time_valid = c;
-                                       break;
-                               case 1:
-                                       return time_valid [0];
-                               default:
-                                       break;
-                               }
-
-                               // again multiple candidates, let's find the AKI that match the SKI (if we have one)
-                               string aki = GetAuthorityKeyIdentifier (child);
-                               if (String.IsNullOrEmpty (aki)) {
-                                       return time_valid [0]; // FIXME: out of luck, you get the first one
-                               }
-                               foreach (X509Certificate2 parent in time_valid) {
-                                       string ski = GetSubjectKeyIdentifier (parent);
-                                       // if both id are available then they must match
-                                       if (aki == ski)
-                                               return parent;
-                               }
-                               return time_valid [0]; // FIXME: out of luck, you get the first one
-                       }
-               }
-
-               private X509Certificate2 FindParent (X509Certificate2 certificate)
-               {
-                       X509Certificate2Collection subset = CertificateCollection.Find (X509FindType.FindBySubjectDistinguishedName, certificate.Issuer, false);
-                       string aki = GetAuthorityKeyIdentifier (certificate);
-                       if ((aki != null) && (aki.Length > 0)) {
-                               subset.AddRange (CertificateCollection.Find (X509FindType.FindBySubjectKeyIdentifier, aki, false));
-                       }
-                       X509Certificate2 parent = SelectBestFromCollection (certificate, subset);
-                       // if parent==certificate we're looping but it's not (probably) a bug and not a true cyclic (over n certs)
-                       return certificate.Equals (parent) ? null : parent;
-               }
-
-               private bool IsChainComplete (X509Certificate2 certificate)
+               public void Dispose ()
                {
-                       // the chain is complete if we have a self-signed certificate
-                       if (!IsSelfIssued (certificate))
-                               return false;
-
-                       // we're very limited to what we can do without certificate extensions
-                       if (certificate.Version < 3)
-                               return true;
-
-                       // check that Authority Key Identifier == Subject Key Identifier
-                       // e.g. it will be different if a self-signed certificate is part (not the end) of the chain
-                       string ski = GetSubjectKeyIdentifier (certificate);
-                       if (String.IsNullOrEmpty (ski))
-                               return true;
-                       string aki = GetAuthorityKeyIdentifier (certificate);
-                       if (String.IsNullOrEmpty (aki))
-                               return true;
-                       // if both id are available then they must match
-                       return (aki == ski);
+                       Dispose (true);
+                       GC.SuppressFinalize (this);
                }
 
-               // check for "self-issued" certificate - without verifying the signature
-               // note that self-issued doesn't always mean it's a root certificate!
-               private bool IsSelfIssued (X509Certificate2 certificate)
+               protected virtual void Dispose (bool disposing)
                {
-                       return (certificate.Issuer == certificate.Subject);
-               }
-
-
-               // *** certificate chain/path validation stuff ***
-
-               // Currently a subset of RFC3280 (hopefully a full implementation someday)
-               private void ValidateChain (X509ChainStatusFlags flag)
-               {
-                       // 'n' should be the root certificate... 
-                       int n = elements.Count - 1;
-                       X509Certificate2 certificate = elements [n].Certificate;
-
-                       // ... and, if so, must be treated outside the chain... 
-                       if (((flag & X509ChainStatusFlags.PartialChain) == 0)) {
-                               Process (n);
-                               // deal with the case where the chain == the root certificate 
-                               // (which isn't for RFC3280) part of the chain
-                               if (n == 0) {
-                                       elements [0].UncompressFlags ();
-                                       return;
-                               }
-                               // skip the root certificate when processing the chain (in 6.1.3)
-                               n--;
-                       }
-                       // ... unless the chain is a partial one (then we start with that one)
-
-                       // 6.1.1 - Inputs
-                       // 6.1.1.a - a prospective certificate path of length n (i.e. elements)
-                       // 6.1.1.b - the current date/time (i.e. ChainPolicy.VerificationTime)
-                       // 6.1.1.c - user-initial-policy-set (i.e. ChainPolicy.CertificatePolicy)
-                       // 6.1.1.d - the trust anchor information (i.e. certificate, unless it's a partial chain)
-                       // 6.1.1.e - initial-policy-mapping-inhibit (NOT SUPPORTED BY THE API)
-                       // 6.1.1.f - initial-explicit-policy (NOT SUPPORTED BY THE API)
-                       // 6.1.1.g - initial-any-policy-inhibit (NOT SUPPORTED BY THE API)
-
-                       // 6.1.2 - Initialization (incomplete)
-                       // 6.1.2.a-f - policy stuff, some TODO, some not supported
-                       // 6.1.2.g - working public key algorithm
-//                     working_public_key_algorithm = certificate.PublicKey.Oid.Value;
-                       // 6.1.2.h-i - our key contains both the "working public key" and "working public key parameters" data
-                       working_public_key = certificate.PublicKey.Key;
-                       // 6.1.2.j - working issuer name
-                       working_issuer_name = certificate.IssuerName;
-                       // 6.1.2.k - this integer is initialized to n, is decremented for each non-self-issued, certificate and
-                       //           may be reduced to the value in the path length constraint field
-                       max_path_length = n;
-
-                       // 6.1.3 - Basic Certificate Processing
-                       // note: loop looks reversed (the list is) but we process this part just like RFC3280 does
-                       for (int i = n; i > 0; i--) {
-                               Process (i);
-                               // 6.1.4 - preparation for certificate i+1 (for not with i+1, or i-1 in our loop)
-                               PrepareForNextCertificate (i);
+                       if (impl != null) {
+                               impl.Dispose ();
+                               impl = null;
                        }
-                       Process (0);
-
-                       // 6.1.3.a.3 - revocation checks
-                       CheckRevocationOnChain (flag);
-
-                       // 6.1.5 - Wrap-up procedure
-                       WrapUp ();
                }
 
-               private void Process (int n)
+               ~X509Chain ()
                {
-                       X509ChainElement element = elements [n];
-                       X509Certificate2 certificate = element.Certificate;
-
-                       // pre-step: DSA certificates may inherit the parameters of their CA
-                       if ((n != elements.Count - 1) && (certificate.MonoCertificate.KeyAlgorithm == "1.2.840.10040.4.1")) {
-                               if (certificate.MonoCertificate.KeyAlgorithmParameters == null) {
-                                       X509Certificate2 parent = elements [n+1].Certificate;
-                                       certificate.MonoCertificate.KeyAlgorithmParameters = parent.MonoCertificate.KeyAlgorithmParameters;
-                               }
-                       }
-
-                       bool root = (working_public_key == null);
-                       // 6.1.3.a.1 - check signature (with special case to deal with root certificates)
-                       if (!IsSignedWith (certificate, root ? certificate.PublicKey.Key : working_public_key)) {
-                               // another special case where only an end-entity is available and can't be verified.
-                               // In this case we do not report an invalid signature (since this is unknown)
-                               if (root || (n != elements.Count - 1) || IsSelfIssued (certificate)) {
-                                       element.StatusFlags |= X509ChainStatusFlags.NotSignatureValid;
-                               }
-                       }
-
-                       // 6.1.3.a.2 - check validity period
-                       if ((ChainPolicy.VerificationTime < certificate.NotBefore) ||
-                               (ChainPolicy.VerificationTime > certificate.NotAfter)) {
-                               element.StatusFlags |= X509ChainStatusFlags.NotTimeValid;
-                       }
-                       // TODO - for X509ChainStatusFlags.NotTimeNested (needs global structure)
-
-                       // note: most of them don't apply to the root certificate
-                       if (root) {
-                               return;
-                       }
-
-                       // 6.1.3.a.3 - revocation check (we're doing at the last stage)
-                       // note: you revoke a trusted root by removing it from your trusted store (i.e. no CRL can do this job)
-
-                       // 6.1.3.a.4 - check certificate issuer name
-                       if (!X500DistinguishedName.AreEqual (certificate.IssuerName, working_issuer_name)) {
-                               // NOTE: this is not the "right" error flag, but it's the closest one defined
-                               element.StatusFlags |= X509ChainStatusFlags.InvalidNameConstraints;
-                       }
-
-                       if (!IsSelfIssued (certificate) && (n != 0)) {
-                               // TODO 6.1.3.b - subject name in the permitted_subtrees ...
-                               // TODO 6.1.3.c - subject name not within excluded_subtrees...
-
-                               // TODO - check for X509ChainStatusFlags.InvalidNameConstraint
-                               // TODO - check for X509ChainStatusFlags.HasNotSupportedNameConstraint
-                               // TODO - check for X509ChainStatusFlags.HasNotPermittedNameConstraint
-                               // TODO - check for X509ChainStatusFlags.HasExcludedNameConstraint
-                       }
-
-                       // TODO 6.1.3.d - check if certificate policies extension is present
-                       //if (false) {
-                               // TODO - for X509ChainStatusFlags.InvalidPolicyConstraints
-                               //      using X509ChainPolicy.ApplicationPolicy and X509ChainPolicy.CertificatePolicy
-
-                               // TODO - check for X509ChainStatusFlags.NoIssuanceChainPolicy
-
-                       //} else {
-                               // TODO 6.1.3.e - set valid_policy_tree to NULL
-                       //}
-
-                       // TODO 6.1.3.f - verify explict_policy > 0 if valid_policy_tree != NULL
-               }
-
-               // CTL == Certificate Trust List / NOT SUPPORTED
-               // TODO - check for X509ChainStatusFlags.CtlNotTimeValid
-               // TODO - check for X509ChainStatusFlags.CtlNotSignatureValid
-               // TODO - check for X509ChainStatusFlags.CtlNotValidForUsage
-
-               private void PrepareForNextCertificate (int n) 
-               {
-                       X509ChainElement element = elements [n];
-                       X509Certificate2 certificate = element.Certificate;
-
-                       // TODO 6.1.4.a-b
-
-                       // 6.1.4.c
-                       working_issuer_name = certificate.SubjectName;
-                       // 6.1.4.d-e - our key includes both the public key and it's parameters
-                       working_public_key = certificate.PublicKey.Key;
-                       // 6.1.4.f
-//                     working_public_key_algorithm = certificate.PublicKey.Oid.Value;
-
-                       // TODO 6.1.4.g-j
-
-                       // 6.1.4.k - Verify that the certificate is a CA certificate
-                       X509BasicConstraintsExtension bce = (certificate.Extensions["2.5.29.19"] as X509BasicConstraintsExtension);
-                       if (bce != null) {
-                               if (!bce.CertificateAuthority) {
-                                       element.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
-                               }
-                       } else if (certificate.Version >= 3) {
-                               // recent (v3+) CA certificates must include BCE
-                               element.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
-                       }
-
-                       // 6.1.4.l - if the certificate isn't self-issued...
-                       if (!IsSelfIssued (certificate)) {
-                               // ... verify that max_path_length > 0
-                               if (max_path_length > 0) {
-                                       max_path_length--;
-                               } else {
-                                       // to match MS the reported status must be against the certificate 
-                                       // with the BCE and not where the path is too long. It also means
-                                       // that this condition has to be reported only once
-                                       if (bce_restriction != null) {
-                                               bce_restriction.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
-                                       }
-                               }
-                       }
-
-                       // 6.1.4.m - if pathLengthConstraint is present...
-                       if ((bce != null) && (bce.HasPathLengthConstraint)) {
-                               // ... and is less that max_path_length, set max_path_length to it's value
-                               if (bce.PathLengthConstraint < max_path_length) {
-                                       max_path_length = bce.PathLengthConstraint;
-                                       bce_restriction = element;
-                               }
-                       }
-
-                       // 6.1.4.n - if key usage extension is present...
-                       X509KeyUsageExtension kue = (certificate.Extensions["2.5.29.15"] as X509KeyUsageExtension);
-                       if (kue != null) {
-                               // ... verify keyCertSign is set
-                               X509KeyUsageFlags success = X509KeyUsageFlags.KeyCertSign;
-                               if ((kue.KeyUsages & success) != success)
-                                       element.StatusFlags |= X509ChainStatusFlags.NotValidForUsage;
-                       }
-
-                       // 6.1.4.o - recognize and process other critical extension present in the certificate
-                       ProcessCertificateExtensions (element);
-               }
-
-               private void WrapUp ()
-               {
-                       X509ChainElement element = elements [0];
-                       X509Certificate2 certificate = element.Certificate;
-
-                       // 6.1.5.a - TODO if certificate n (our 0) wasn't self issued and explicit_policy != 0
-                       if (IsSelfIssued (certificate)) {
-                               // TODO... decrement explicit_policy by 1
-                       }
-
-                       // 6.1.5.b - TODO
-
-                       // 6.1.5.c,d,e - not required by the X509Chain implementation
-
-                       // 6.1.5.f - recognize and process other critical extension present in the certificate
-                       ProcessCertificateExtensions (element);
-
-                       // 6.1.5.g - TODO
-
-                       // uncompressed the flags into several elements
-                       for (int i = elements.Count - 1; i >= 0; i--) {
-                               elements [i].UncompressFlags ();
-                       }
-               }
-
-               private void ProcessCertificateExtensions (X509ChainElement element)
-               {
-                       foreach (X509Extension ext in element.Certificate.Extensions) {
-                               if (ext.Critical) {
-                                       switch (ext.Oid.Value) {
-                                       case "2.5.29.15": // X509KeyUsageExtension
-                                       case "2.5.29.19": // X509BasicConstraintsExtension
-                                               // we processed this extension
-                                               break;
-                                       default:
-                                               // note: Under Windows XP MS implementation seems to ignore 
-                                               // certificate with unknown critical extensions.
-                                               element.StatusFlags |= X509ChainStatusFlags.InvalidExtension;
-                                               break;
-                                       }
-                               }
-                       }
-               }
-
-               private bool IsSignedWith (X509Certificate2 signed, AsymmetricAlgorithm pubkey)
-               {
-                       if (pubkey == null)
-                               return false;
-                       // Sadly X509Certificate2 doesn't expose the signature nor the tbs (to be signed) structure
-                       MX.X509Certificate mx = signed.MonoCertificate;
-                       return (mx.VerifySignature (pubkey));
-               }
-
-               private string GetSubjectKeyIdentifier (X509Certificate2 certificate)
-               {
-                       X509SubjectKeyIdentifierExtension ski = (certificate.Extensions["2.5.29.14"] as X509SubjectKeyIdentifierExtension);
-                       return (ski == null) ? String.Empty : ski.SubjectKeyIdentifier;
-               }
-
-               // System.dll v2 doesn't have a class to deal with the AuthorityKeyIdentifier extension
-               static string GetAuthorityKeyIdentifier (X509Certificate2 certificate)
-               {
-                       return GetAuthorityKeyIdentifier (certificate.MonoCertificate.Extensions ["2.5.29.35"]);
-               }
-
-               // but anyway System.dll v2 doesn't expose CRL in any way so...
-               static string GetAuthorityKeyIdentifier (MX.X509Crl crl)
-               {
-                       return GetAuthorityKeyIdentifier (crl.Extensions ["2.5.29.35"]);
-               }
-
-               static string GetAuthorityKeyIdentifier (MX.X509Extension ext)
-               {
-                       if (ext == null)
-                               return String.Empty;
-                       MX.Extensions.AuthorityKeyIdentifierExtension aki = new MX.Extensions.AuthorityKeyIdentifierExtension (ext);
-                       byte[] id = aki.Identifier;
-                       if (id == null) 
-                               return String.Empty;
-                       StringBuilder sb = new StringBuilder ();
-                       foreach (byte b in id)
-                               sb.Append (b.ToString ("X02"));
-                       return sb.ToString ();
-               }
-
-               // we check the revocation only once we have built the complete chain
-               private void CheckRevocationOnChain (X509ChainStatusFlags flag)
-               {
-                       bool partial = ((flag & X509ChainStatusFlags.PartialChain) != 0);
-                       bool online;
-
-                       switch (ChainPolicy.RevocationMode) {
-                       case X509RevocationMode.Online:
-                               // default
-                               online = true;
-                               break;
-                       case X509RevocationMode.Offline:
-                               online = false;
-                               break;
-                       case X509RevocationMode.NoCheck:
-                               return;
-                       default:
-                               throw new InvalidOperationException (Locale.GetText ("Invalid revocation mode."));
-                       }
-
-                       bool unknown = partial;
-                       // from the root down to the end-entity
-                       for (int i = elements.Count - 1; i >= 0; i--) {
-                               bool check = true;
-
-                               switch (ChainPolicy.RevocationFlag) {
-                               case X509RevocationFlag.EndCertificateOnly:
-                                       check = (i == 0);
-                                       break;
-                               case X509RevocationFlag.EntireChain:
-                                       check = true;
-                                       break;
-                               case X509RevocationFlag.ExcludeRoot:
-                                       // default
-                                       check = (i != (elements.Count - 1));
-                                       // anyway, who's gonna sign that the root is invalid ?
-                                       break;
-                               }
-
-                               X509ChainElement element = elements [i];
-
-                               // we can't assume the revocation status if the certificate is bad (e.g. invalid signature)
-                               if (!unknown)
-                                       unknown |= ((element.StatusFlags & X509ChainStatusFlags.NotSignatureValid) != 0);
-
-                               if (unknown) {
-                                       // we can skip the revocation checks as we can't be sure of them anyway
-                                       element.StatusFlags |= X509ChainStatusFlags.RevocationStatusUnknown;
-                                       element.StatusFlags |= X509ChainStatusFlags.OfflineRevocation;
-                               } else if (check && !partial && !IsSelfIssued (element.Certificate)) {
-                                       // check for revocation (except for the trusted root and self-issued certs)
-                                       element.StatusFlags |= CheckRevocation (element.Certificate, i+1, online);
-                                       // if revoked, then all others following in the chain are unknown...
-                                       unknown |= ((element.StatusFlags & X509ChainStatusFlags.Revoked) != 0);
-                               }
-                       }
-               }
-
-               // This isn't how RFC3280 (section 6.3) deals with CRL, but then we don't (yet) support DP, deltas...
-               private X509ChainStatusFlags CheckRevocation (X509Certificate2 certificate, int ca, bool online)
-               {
-                       X509ChainStatusFlags result = X509ChainStatusFlags.RevocationStatusUnknown;
-                       X509ChainElement element = elements [ca];
-                       X509Certificate2 ca_cert = element.Certificate;
-
-                       // find the CRL from the "right" CA
-                       while (IsSelfIssued (ca_cert) && (ca < elements.Count - 1)) {
-                               // try with this self-issued
-                               result = CheckRevocation (certificate, ca_cert, online);
-                               if (result != X509ChainStatusFlags.RevocationStatusUnknown)
-                                       break;
-                               ca++;
-                               element = elements [ca];
-                               ca_cert = element.Certificate;
-                       }
-                       if (result == X509ChainStatusFlags.RevocationStatusUnknown)
-                               result = CheckRevocation (certificate, ca_cert, online);
-                       return result;
-               }
-
-               private X509ChainStatusFlags CheckRevocation (X509Certificate2 certificate, X509Certificate2 ca_cert, bool online)
-               {
-                       // change this if/when we support OCSP
-                       X509KeyUsageExtension kue = (ca_cert.Extensions["2.5.29.15"] as X509KeyUsageExtension);
-                       if (kue != null) {
-                               // ... verify CrlSign is set
-                               X509KeyUsageFlags success = X509KeyUsageFlags.CrlSign;
-                               if ((kue.KeyUsages & success) != success) {
-                                       // FIXME - we should try to find an alternative CA that has the CrlSign bit
-                                       return X509ChainStatusFlags.RevocationStatusUnknown;
-                               }
-                       }
-
-                       MX.X509Crl crl = FindCrl (ca_cert);
-
-                       if ((crl == null) && online) {
-                               // FIXME - download and install new CRL
-                               // then you get a second chance
-                               // crl = FindCrl (ca_cert, ref valid, ref out_of_date);
-
-                               // We need to get the subjectAltName and an URI from there (or use OCSP)        
-                               // X509KeyUsageExtension subjectAltName = (ca_cert.Extensions["2.5.29.17"] as X509KeyUsageExtension);
-                       }
-
-                       if (crl != null) {
-                               // validate the digital signature on the CRL using the CA public key
-                               // note #1: we can't use X509Crl.VerifySignature(X509Certificate) because it duplicates
-                               // checks and we loose the "why" of the failure
-                               // note #2: we do this before other tests as an invalid signature could be a hacked CRL
-                               // (so anything within can't be trusted)
-                               if (!crl.VerifySignature (ca_cert.PublicKey.Key)) {
-                                       return X509ChainStatusFlags.RevocationStatusUnknown;
-                               }
-
-                               MX.X509Crl.X509CrlEntry entry = crl.GetCrlEntry (certificate.MonoCertificate);
-                               if (entry != null) {
-                                       // We have an entry for this CRL that includes an unknown CRITICAL extension
-                                       // See [X.509 7.3] NOTE 4
-                                       if (!ProcessCrlEntryExtensions (entry))
-                                               return X509ChainStatusFlags.Revoked;
-
-                                       // FIXME - a little more is involved
-                                       if (entry.RevocationDate <= ChainPolicy.VerificationTime)
-                                               return X509ChainStatusFlags.Revoked;
-                               }
-
-                               // are we overdue for a CRL update ? if so we can't be sure of any certificate status
-                               if (crl.NextUpdate < ChainPolicy.VerificationTime)
-                                       return X509ChainStatusFlags.RevocationStatusUnknown | X509ChainStatusFlags.OfflineRevocation;
-
-                               // we have a CRL that includes an unknown CRITICAL extension
-                               // we put this check at the end so we do not "hide" any Revoked flags
-                               if (!ProcessCrlExtensions (crl)) {
-                                       return X509ChainStatusFlags.RevocationStatusUnknown;
-                               }
-                       } else {
-                               return X509ChainStatusFlags.RevocationStatusUnknown;
-                       }
-
-                       return X509ChainStatusFlags.NoError;
-               }
-
-               static MX.X509Crl CheckCrls (string subject, string ski, MX.X509Store store)
-               {
-                       if (store == null)
-                               return null;
-
-                       var crls = store.Crls;
-                       foreach (MX.X509Crl crl in crls) {
-                               if (crl.IssuerName == subject && (ski.Length == 0 || ski == GetAuthorityKeyIdentifier (crl)))
-                                       return crl;
-                       }
-                       return null; // No CRL found
-               }
-
-               private MX.X509Crl FindCrl (X509Certificate2 caCertificate)
-               {
-                       string subject = caCertificate.SubjectName.Decode (X500DistinguishedNameFlags.None);
-                       string ski = GetSubjectKeyIdentifier (caCertificate);
-
-                       // consider that the LocalMachine directories could not exists... and cannot be created by the user
-                       MX.X509Crl result = CheckCrls (subject, ski, LMCAStore.Store);
-                       if (result != null)
-                               return result;
-                       if (location == StoreLocation.CurrentUser) {
-                               result = CheckCrls (subject, ski, UserCAStore.Store);
-                               if (result != null)
-                                       return result;
-                       }
-
-                       // consider that the LocalMachine directories could not exists... and cannot be created by the user
-                       result = CheckCrls (subject, ski, LMRootStore.Store);
-                       if (result != null)
-                               return result;
-                       if (location == StoreLocation.CurrentUser) {
-                               result = CheckCrls (subject, ski, UserRootStore.Store);
-                               if (result != null)
-                                       return result;
-                       }
-                       return null;
-               }
-
-               private bool ProcessCrlExtensions (MX.X509Crl crl)
-               {
-                       foreach (MX.X509Extension ext in crl.Extensions) {
-                               if (ext.Critical) {
-                                       switch (ext.Oid) {
-                                       case "2.5.29.20": // cRLNumber
-                                       case "2.5.29.35": // authorityKeyIdentifier
-                                               // we processed/know about this extension
-                                               break;
-                                       default:
-                                               return false;
-                                       }
-                               }
-                       }
-                       return true;
-               }
-
-               private bool ProcessCrlEntryExtensions (MX.X509Crl.X509CrlEntry entry)
-               {
-                       foreach (MX.X509Extension ext in entry.Extensions) {
-                               if (ext.Critical) {
-                                       switch (ext.Oid) {
-                                       case "2.5.29.21": // cRLReason
-                                               // we processed/know about this extension
-                                               break;
-                                       default:
-                                               return false;
-                                       }
-                               }
-                       }
-                       return true;
+                       Dispose (false);
                }
        }
 }
diff --git a/mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImpl.cs b/mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImpl.cs
new file mode 100644 (file)
index 0000000..2a4c9cf
--- /dev/null
@@ -0,0 +1,81 @@
+//
+// X509ChainImpl.cs
+//
+// Authors:
+//     Martin Baulig  <martin.baulig@xamarin.com>
+//
+// Copyright (C) 2016 Xamarin, Inc. (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+#if SECURITY_DEP
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       internal abstract class X509ChainImpl : IDisposable
+       {
+               public abstract bool IsValid {
+                       get;
+               }
+
+               public abstract IntPtr Handle {
+                       get;
+               }
+
+               protected void ThrowIfContextInvalid ()
+               {
+                       if (!IsValid)
+                               throw X509Helper2.GetInvalidChainContextException ();
+               }
+
+               public abstract X509ChainElementCollection ChainElements {
+                       get;
+               }
+
+               public abstract X509ChainPolicy ChainPolicy {
+                       get; set;
+               }
+
+               public abstract X509ChainStatus[] ChainStatus {
+                       get;
+               }
+
+               public abstract bool Build (X509Certificate2 certificate);
+
+               public abstract void Reset ();
+
+               public void Dispose ()
+               {
+                       Dispose (true);
+                       GC.SuppressFinalize (this);
+               }
+
+               protected virtual void Dispose (bool disposing)
+               {
+               }
+
+               ~X509ChainImpl ()
+               {
+                       Dispose (false);
+               }
+       }
+}
+
+#endif
diff --git a/mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImplMono.cs b/mcs/class/System/System.Security.Cryptography.X509Certificates/X509ChainImplMono.cs
new file mode 100644 (file)
index 0000000..210bd8f
--- /dev/null
@@ -0,0 +1,954 @@
+//
+// System.Security.Cryptography.X509Certificates.X509ChainImplMono
+//
+// Author:
+//     Sebastien Pouliot  <sebastien@ximian.com>
+//
+// (C) 2003 Motus Technologies Inc. (http://www.motus.com)
+// Copyright (C) 2004-2006 Novell Inc. (http://www.novell.com)
+// Copyright (C) 2011 Xamarin Inc. (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+#if SECURITY_DEP
+
+#if MONO_SECURITY_ALIAS
+extern alias MonoSecurity;
+using MX = MonoSecurity::Mono.Security.X509;
+#else
+using MX = Mono.Security.X509;
+#endif
+
+using System.Collections;
+using System.Text;
+
+namespace System.Security.Cryptography.X509Certificates {
+
+       internal class X509ChainImplMono : X509ChainImpl
+       {
+               private StoreLocation location;
+               private X509ChainElementCollection elements;
+               private X509ChainPolicy policy;
+               private X509ChainStatus[] status;
+
+               static X509ChainStatus[] Empty = new X509ChainStatus [0];
+
+               // RFC3280 variables
+               private int max_path_length;
+               private X500DistinguishedName working_issuer_name;
+//             private string working_public_key_algorithm;
+               private AsymmetricAlgorithm working_public_key;
+
+               // other flags
+               private X509ChainElement bce_restriction;
+
+               // constructors
+
+               public X509ChainImplMono ()
+                       : this (false)
+               {
+               }
+
+               public X509ChainImplMono (bool useMachineContext) 
+               {
+                       location = useMachineContext ? StoreLocation.LocalMachine : StoreLocation.CurrentUser;
+                       elements = new X509ChainElementCollection ();
+                       policy = new X509ChainPolicy ();
+               }
+
+               [MonoTODO ("Mono's X509Chain is fully managed. All handles are invalid.")]
+               public X509ChainImplMono (IntPtr chainContext)
+               {
+                       // CryptoAPI compatibility (unmanaged handle)
+                       throw new NotSupportedException ();
+               }
+
+               public override bool IsValid {
+                       get { return true; }
+               }
+
+               public override IntPtr Handle {
+                       get { return IntPtr.Zero; }
+               }
+
+               // properties
+
+               public override X509ChainElementCollection ChainElements {
+                       get { return elements; }
+               }
+
+               public override X509ChainPolicy ChainPolicy {
+                       get { return policy; }
+                       set { policy = value; }
+               }
+
+               public override X509ChainStatus[] ChainStatus {
+                       get { 
+                               if (status == null)
+                                       return Empty;
+                               return status;
+                       }
+               } 
+
+               // methods
+
+               [MonoTODO ("Not totally RFC3280 compliant, but neither is MS implementation...")]
+               public override bool Build (X509Certificate2 certificate)
+               {
+                       if (certificate == null)
+                               throw new ArgumentException ("certificate");
+
+                       Reset ();
+                       X509ChainStatusFlags flag;
+                       try {
+                               flag = BuildChainFrom (certificate);
+                               ValidateChain (flag);
+                       }
+                       catch (CryptographicException ce) {
+                               throw new ArgumentException ("certificate", ce);
+                       }
+
+                       X509ChainStatusFlags total = X509ChainStatusFlags.NoError;
+                       ArrayList list = new ArrayList ();
+                       // build "global" ChainStatus from the ChainStatus of every ChainElements
+                       foreach (X509ChainElement ce in elements) {
+                               foreach (X509ChainStatus cs in ce.ChainElementStatus) {
+                                       // we MUST avoid duplicates in the "global" list
+                                       if ((total & cs.Status) != cs.Status) {
+                                               list.Add (cs);
+                                               total |= cs.Status;
+                                       }
+                               }
+                       }
+                       // and if required add some
+                       if (flag != X509ChainStatusFlags.NoError) {
+                               list.Insert (0, new X509ChainStatus (flag));
+                       }
+                       status = (X509ChainStatus[]) list.ToArray (typeof (X509ChainStatus));
+
+                       // (fast path) this ignore everything we have checked
+                       if ((status.Length == 0) || (ChainPolicy.VerificationFlags == X509VerificationFlags.AllFlags))
+                               return true;
+
+                       bool result = true;
+                       // now check if exclude some verification for the "end result" (boolean)
+                       foreach (X509ChainStatus cs in status) {
+                               switch (cs.Status) {
+                               case X509ChainStatusFlags.UntrustedRoot:
+                               case X509ChainStatusFlags.PartialChain:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.AllowUnknownCertificateAuthority) != 0);
+                                       break;
+                               case X509ChainStatusFlags.NotTimeValid:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreNotTimeValid) != 0);
+                                       break;
+                               // FIXME - from here we needs new test cases for all cases
+                               case X509ChainStatusFlags.NotTimeNested:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreNotTimeNested) != 0);
+                                       break;
+                               case X509ChainStatusFlags.InvalidBasicConstraints:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidBasicConstraints) != 0);
+                                       break;
+                               case X509ChainStatusFlags.InvalidPolicyConstraints:
+                               case X509ChainStatusFlags.NoIssuanceChainPolicy:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidPolicy) != 0);
+                                       break;
+                               case X509ChainStatusFlags.InvalidNameConstraints:
+                               case X509ChainStatusFlags.HasNotSupportedNameConstraint:
+                               case X509ChainStatusFlags.HasNotPermittedNameConstraint:
+                               case X509ChainStatusFlags.HasExcludedNameConstraint:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreInvalidName) != 0);
+                                       break;
+                               case X509ChainStatusFlags.InvalidExtension:
+                                       // not sure ?!?
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreWrongUsage) != 0);
+                                       break;
+                               //
+                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreRootRevocationUnknown) != 0)
+                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreEndRevocationUnknown) != 0)
+                               case X509ChainStatusFlags.CtlNotTimeValid:
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreCtlNotTimeValid) != 0);
+                                       break;
+                               case X509ChainStatusFlags.CtlNotSignatureValid:
+                                       // ?
+                                       break;
+                               //      ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreCtlSignerRevocationUnknown) != 0);
+                               case X509ChainStatusFlags.CtlNotValidForUsage:
+                                       // FIXME - does IgnoreWrongUsage apply to CTL (it doesn't have Ctl in it's name like the others)
+                                       result &= ((ChainPolicy.VerificationFlags & X509VerificationFlags.IgnoreWrongUsage) != 0);
+                                       break;
+                               default:
+                                       result = false;
+                                       break;
+                               }
+                               // once we have one failure there's no need to check further
+                               if (!result)
+                                       return false;
+                       }
+
+                       // every "problem" was excluded
+                       return true;
+               }
+
+               public override void Reset () 
+               {
+                       // note: this call doesn't Reset the X509ChainPolicy
+                       if ((status != null) && (status.Length != 0))
+                               status = null;
+                       if (elements.Count > 0)
+                               elements.Clear ();
+                       if (user_root_store != null) {
+                               user_root_store.Close ();
+                               user_root_store = null;
+                       }
+                       if (root_store != null) {
+                               root_store.Close ();
+                               root_store = null;
+                       }
+                       if (user_ca_store != null) {
+                               user_ca_store.Close ();
+                               user_ca_store = null;
+                       }
+                       if (ca_store != null) {
+                               ca_store.Close ();
+                               ca_store = null;
+                       }
+                       roots = null;
+                       cas = null;
+                       collection = null;
+                       bce_restriction = null;
+                       working_public_key = null;
+               }
+
+               // private stuff
+
+               private X509Certificate2Collection roots;
+               private X509Certificate2Collection cas;
+               private X509Store root_store;
+               private X509Store ca_store;
+               private X509Store user_root_store;
+               private X509Store user_ca_store;
+
+               private X509Certificate2Collection Roots {
+                       get {
+                               if (roots == null) {
+                                       X509Certificate2Collection c = new X509Certificate2Collection ();
+                                       X509Store store = LMRootStore;
+                                       if (location == StoreLocation.CurrentUser)
+                                               c.AddRange (UserRootStore.Certificates);
+                                       c.AddRange (store.Certificates);
+                                       roots = c;
+                               }
+                               return roots;
+                       }
+               }
+
+               private X509Certificate2Collection CertificateAuthorities {
+                       get {
+                               if (cas == null) {
+                                       X509Certificate2Collection c = new X509Certificate2Collection ();
+                                       X509Store store = LMCAStore;
+                                       if (location == StoreLocation.CurrentUser)
+                                               c.AddRange (UserCAStore.Certificates);
+                                       c.AddRange (store.Certificates);
+                                       cas = c;
+                               }
+                               return cas;
+                       }
+               }
+
+               private X509Store LMRootStore {
+                       get {
+                               if (root_store == null) {
+                                       root_store = new X509Store (StoreName.Root, StoreLocation.LocalMachine);
+                                       try {
+                                               root_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
+                                       } catch {
+                                       }
+                               }
+                               return root_store;
+                       }
+               }
+
+               private X509Store UserRootStore {
+                       get {
+                               if (user_root_store == null) {
+                                       user_root_store = new X509Store (StoreName.Root, StoreLocation.CurrentUser);
+                                       try {
+                                               user_root_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
+                                       } catch {
+                                       }
+                               }
+                               return user_root_store;
+                       }
+               }
+
+               private X509Store LMCAStore {
+                       get {
+                               if (ca_store == null) {
+                                       ca_store = new X509Store (StoreName.CertificateAuthority, StoreLocation.LocalMachine);
+                                       try {
+                                               ca_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
+                                       } catch {
+                                       }
+                               }
+                               return ca_store;
+                       }
+               }
+
+               private X509Store UserCAStore {
+                       get {
+                               if (user_ca_store == null) {
+                                       user_ca_store = new X509Store (StoreName.CertificateAuthority, StoreLocation.CurrentUser);
+                                       try {
+                                               user_ca_store.Open (OpenFlags.OpenExistingOnly | OpenFlags.ReadOnly);
+                                       } catch {
+                                       }
+                               }
+                               return user_ca_store;
+                       }
+               }
+               // *** certificate chain/path building stuff ***
+
+               private X509Certificate2Collection collection;
+
+               // we search local user (default) or machine certificate store 
+               // and in the extra certificate supplied in ChainPolicy.ExtraStore
+               private X509Certificate2Collection CertificateCollection {
+                       get {
+                               if (collection == null) {
+                                       collection = new X509Certificate2Collection (ChainPolicy.ExtraStore);
+                                       collection.AddRange (Roots);
+                                       collection.AddRange (CertificateAuthorities);
+                               }
+                               return collection;
+                       }
+               }
+
+               // This is a non-recursive chain/path building algorithm. 
+               //
+               // At this stage we only checks for PartialChain, Cyclic and UntrustedRoot errors are they
+               // affect the path building (other errors are verification errors).
+               //
+               // Note that the order match the one we need to match MS and not the one defined in RFC3280,
+               // we also include the trusted root certificate (trust anchor in RFC3280) in the list.
+               // (this isn't an issue, just keep that in mind if you look at the source and the RFC)
+               private X509ChainStatusFlags BuildChainFrom (X509Certificate2 certificate)
+               {
+                       elements.Add (certificate);
+
+                       while (!IsChainComplete (certificate)) {
+                               certificate = FindParent (certificate);
+
+                               if (certificate == null)
+                                       return X509ChainStatusFlags.PartialChain;
+
+                               if (elements.Contains (certificate))
+                                       return X509ChainStatusFlags.Cyclic;
+
+                               elements.Add (certificate);
+                       }
+
+                       // roots may be supplied (e.g. in the ExtraStore) so we need to confirm their
+                       // trustiness (what a cute word) in the trusted root collection
+                       if (!Roots.Contains (certificate))
+                               elements [elements.Count - 1].StatusFlags |= X509ChainStatusFlags.UntrustedRoot;
+
+                       return X509ChainStatusFlags.NoError;
+               }
+
+
+               private X509Certificate2 SelectBestFromCollection (X509Certificate2 child, X509Certificate2Collection c)
+               {
+                       switch (c.Count) {
+                       case 0:
+                               return null;
+                       case 1:
+                               return c [0];
+                       default:
+                               // multiple candidate, keep only the ones that are still valid
+                               X509Certificate2Collection time_valid = c.Find (X509FindType.FindByTimeValid, ChainPolicy.VerificationTime, false);
+                               switch (time_valid.Count) {
+                               case 0:
+                                       // that's too restrictive, let's revert and try another thing...
+                                       time_valid = c;
+                                       break;
+                               case 1:
+                                       return time_valid [0];
+                               default:
+                                       break;
+                               }
+
+                               // again multiple candidates, let's find the AKI that match the SKI (if we have one)
+                               string aki = GetAuthorityKeyIdentifier (child);
+                               if (String.IsNullOrEmpty (aki)) {
+                                       return time_valid [0]; // FIXME: out of luck, you get the first one
+                               }
+                               foreach (X509Certificate2 parent in time_valid) {
+                                       string ski = GetSubjectKeyIdentifier (parent);
+                                       // if both id are available then they must match
+                                       if (aki == ski)
+                                               return parent;
+                               }
+                               return time_valid [0]; // FIXME: out of luck, you get the first one
+                       }
+               }
+
+               private X509Certificate2 FindParent (X509Certificate2 certificate)
+               {
+                       X509Certificate2Collection subset = CertificateCollection.Find (X509FindType.FindBySubjectDistinguishedName, certificate.Issuer, false);
+                       string aki = GetAuthorityKeyIdentifier (certificate);
+                       if ((aki != null) && (aki.Length > 0)) {
+                               subset.AddRange (CertificateCollection.Find (X509FindType.FindBySubjectKeyIdentifier, aki, false));
+                       }
+                       X509Certificate2 parent = SelectBestFromCollection (certificate, subset);
+                       // if parent==certificate we're looping but it's not (probably) a bug and not a true cyclic (over n certs)
+                       return certificate.Equals (parent) ? null : parent;
+               }
+
+               private bool IsChainComplete (X509Certificate2 certificate)
+               {
+                       // the chain is complete if we have a self-signed certificate
+                       if (!IsSelfIssued (certificate))
+                               return false;
+
+                       // we're very limited to what we can do without certificate extensions
+                       if (certificate.Version < 3)
+                               return true;
+
+                       // check that Authority Key Identifier == Subject Key Identifier
+                       // e.g. it will be different if a self-signed certificate is part (not the end) of the chain
+                       string ski = GetSubjectKeyIdentifier (certificate);
+                       if (String.IsNullOrEmpty (ski))
+                               return true;
+                       string aki = GetAuthorityKeyIdentifier (certificate);
+                       if (String.IsNullOrEmpty (aki))
+                               return true;
+                       // if both id are available then they must match
+                       return (aki == ski);
+               }
+
+               // check for "self-issued" certificate - without verifying the signature
+               // note that self-issued doesn't always mean it's a root certificate!
+               private bool IsSelfIssued (X509Certificate2 certificate)
+               {
+                       return (certificate.Issuer == certificate.Subject);
+               }
+
+
+               // *** certificate chain/path validation stuff ***
+
+               // Currently a subset of RFC3280 (hopefully a full implementation someday)
+               private void ValidateChain (X509ChainStatusFlags flag)
+               {
+                       // 'n' should be the root certificate... 
+                       int n = elements.Count - 1;
+                       X509Certificate2 certificate = elements [n].Certificate;
+
+                       // ... and, if so, must be treated outside the chain... 
+                       if (((flag & X509ChainStatusFlags.PartialChain) == 0)) {
+                               Process (n);
+                               // deal with the case where the chain == the root certificate 
+                               // (which isn't for RFC3280) part of the chain
+                               if (n == 0) {
+                                       elements [0].UncompressFlags ();
+                                       return;
+                               }
+                               // skip the root certificate when processing the chain (in 6.1.3)
+                               n--;
+                       }
+                       // ... unless the chain is a partial one (then we start with that one)
+
+                       // 6.1.1 - Inputs
+                       // 6.1.1.a - a prospective certificate path of length n (i.e. elements)
+                       // 6.1.1.b - the current date/time (i.e. ChainPolicy.VerificationTime)
+                       // 6.1.1.c - user-initial-policy-set (i.e. ChainPolicy.CertificatePolicy)
+                       // 6.1.1.d - the trust anchor information (i.e. certificate, unless it's a partial chain)
+                       // 6.1.1.e - initial-policy-mapping-inhibit (NOT SUPPORTED BY THE API)
+                       // 6.1.1.f - initial-explicit-policy (NOT SUPPORTED BY THE API)
+                       // 6.1.1.g - initial-any-policy-inhibit (NOT SUPPORTED BY THE API)
+
+                       // 6.1.2 - Initialization (incomplete)
+                       // 6.1.2.a-f - policy stuff, some TODO, some not supported
+                       // 6.1.2.g - working public key algorithm
+//                     working_public_key_algorithm = certificate.PublicKey.Oid.Value;
+                       // 6.1.2.h-i - our key contains both the "working public key" and "working public key parameters" data
+                       working_public_key = certificate.PublicKey.Key;
+                       // 6.1.2.j - working issuer name
+                       working_issuer_name = certificate.IssuerName;
+                       // 6.1.2.k - this integer is initialized to n, is decremented for each non-self-issued, certificate and
+                       //           may be reduced to the value in the path length constraint field
+                       max_path_length = n;
+
+                       // 6.1.3 - Basic Certificate Processing
+                       // note: loop looks reversed (the list is) but we process this part just like RFC3280 does
+                       for (int i = n; i > 0; i--) {
+                               Process (i);
+                               // 6.1.4 - preparation for certificate i+1 (for not with i+1, or i-1 in our loop)
+                               PrepareForNextCertificate (i);
+                       }
+                       Process (0);
+
+                       // 6.1.3.a.3 - revocation checks
+                       CheckRevocationOnChain (flag);
+
+                       // 6.1.5 - Wrap-up procedure
+                       WrapUp ();
+               }
+
+               private void Process (int n)
+               {
+                       X509ChainElement element = elements [n];
+                       X509Certificate2 certificate = element.Certificate;
+
+                       // pre-step: DSA certificates may inherit the parameters of their CA
+                       if ((n != elements.Count - 1) && (certificate.MonoCertificate.KeyAlgorithm == "1.2.840.10040.4.1")) {
+                               if (certificate.MonoCertificate.KeyAlgorithmParameters == null) {
+                                       X509Certificate2 parent = elements [n+1].Certificate;
+                                       certificate.MonoCertificate.KeyAlgorithmParameters = parent.MonoCertificate.KeyAlgorithmParameters;
+                               }
+                       }
+
+                       bool root = (working_public_key == null);
+                       // 6.1.3.a.1 - check signature (with special case to deal with root certificates)
+                       if (!IsSignedWith (certificate, root ? certificate.PublicKey.Key : working_public_key)) {
+                               // another special case where only an end-entity is available and can't be verified.
+                               // In this case we do not report an invalid signature (since this is unknown)
+                               if (root || (n != elements.Count - 1) || IsSelfIssued (certificate)) {
+                                       element.StatusFlags |= X509ChainStatusFlags.NotSignatureValid;
+                               }
+                       }
+
+                       // 6.1.3.a.2 - check validity period
+                       if ((ChainPolicy.VerificationTime < certificate.NotBefore) ||
+                               (ChainPolicy.VerificationTime > certificate.NotAfter)) {
+                               element.StatusFlags |= X509ChainStatusFlags.NotTimeValid;
+                       }
+                       // TODO - for X509ChainStatusFlags.NotTimeNested (needs global structure)
+
+                       // note: most of them don't apply to the root certificate
+                       if (root) {
+                               return;
+                       }
+
+                       // 6.1.3.a.3 - revocation check (we're doing at the last stage)
+                       // note: you revoke a trusted root by removing it from your trusted store (i.e. no CRL can do this job)
+
+                       // 6.1.3.a.4 - check certificate issuer name
+                       if (!X500DistinguishedName.AreEqual (certificate.IssuerName, working_issuer_name)) {
+                               // NOTE: this is not the "right" error flag, but it's the closest one defined
+                               element.StatusFlags |= X509ChainStatusFlags.InvalidNameConstraints;
+                       }
+
+                       if (!IsSelfIssued (certificate) && (n != 0)) {
+                               // TODO 6.1.3.b - subject name in the permitted_subtrees ...
+                               // TODO 6.1.3.c - subject name not within excluded_subtrees...
+
+                               // TODO - check for X509ChainStatusFlags.InvalidNameConstraint
+                               // TODO - check for X509ChainStatusFlags.HasNotSupportedNameConstraint
+                               // TODO - check for X509ChainStatusFlags.HasNotPermittedNameConstraint
+                               // TODO - check for X509ChainStatusFlags.HasExcludedNameConstraint
+                       }
+
+                       // TODO 6.1.3.d - check if certificate policies extension is present
+                       //if (false) {
+                               // TODO - for X509ChainStatusFlags.InvalidPolicyConstraints
+                               //      using X509ChainPolicy.ApplicationPolicy and X509ChainPolicy.CertificatePolicy
+
+                               // TODO - check for X509ChainStatusFlags.NoIssuanceChainPolicy
+
+                       //} else {
+                               // TODO 6.1.3.e - set valid_policy_tree to NULL
+                       //}
+
+                       // TODO 6.1.3.f - verify explict_policy > 0 if valid_policy_tree != NULL
+               }
+
+               // CTL == Certificate Trust List / NOT SUPPORTED
+               // TODO - check for X509ChainStatusFlags.CtlNotTimeValid
+               // TODO - check for X509ChainStatusFlags.CtlNotSignatureValid
+               // TODO - check for X509ChainStatusFlags.CtlNotValidForUsage
+
+               private void PrepareForNextCertificate (int n) 
+               {
+                       X509ChainElement element = elements [n];
+                       X509Certificate2 certificate = element.Certificate;
+
+                       // TODO 6.1.4.a-b
+
+                       // 6.1.4.c
+                       working_issuer_name = certificate.SubjectName;
+                       // 6.1.4.d-e - our key includes both the public key and it's parameters
+                       working_public_key = certificate.PublicKey.Key;
+                       // 6.1.4.f
+//                     working_public_key_algorithm = certificate.PublicKey.Oid.Value;
+
+                       // TODO 6.1.4.g-j
+
+                       // 6.1.4.k - Verify that the certificate is a CA certificate
+                       X509BasicConstraintsExtension bce = (certificate.Extensions["2.5.29.19"] as X509BasicConstraintsExtension);
+                       if (bce != null) {
+                               if (!bce.CertificateAuthority) {
+                                       element.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
+                               }
+                       } else if (certificate.Version >= 3) {
+                               // recent (v3+) CA certificates must include BCE
+                               element.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
+                       }
+
+                       // 6.1.4.l - if the certificate isn't self-issued...
+                       if (!IsSelfIssued (certificate)) {
+                               // ... verify that max_path_length > 0
+                               if (max_path_length > 0) {
+                                       max_path_length--;
+                               } else {
+                                       // to match MS the reported status must be against the certificate 
+                                       // with the BCE and not where the path is too long. It also means
+                                       // that this condition has to be reported only once
+                                       if (bce_restriction != null) {
+                                               bce_restriction.StatusFlags |= X509ChainStatusFlags.InvalidBasicConstraints;
+                                       }
+                               }
+                       }
+
+                       // 6.1.4.m - if pathLengthConstraint is present...
+                       if ((bce != null) && (bce.HasPathLengthConstraint)) {
+                               // ... and is less that max_path_length, set max_path_length to it's value
+                               if (bce.PathLengthConstraint < max_path_length) {
+                                       max_path_length = bce.PathLengthConstraint;
+                                       bce_restriction = element;
+                               }
+                       }
+
+                       // 6.1.4.n - if key usage extension is present...
+                       X509KeyUsageExtension kue = (certificate.Extensions["2.5.29.15"] as X509KeyUsageExtension);
+                       if (kue != null) {
+                               // ... verify keyCertSign is set
+                               X509KeyUsageFlags success = X509KeyUsageFlags.KeyCertSign;
+                               if ((kue.KeyUsages & success) != success)
+                                       element.StatusFlags |= X509ChainStatusFlags.NotValidForUsage;
+                       }
+
+                       // 6.1.4.o - recognize and process other critical extension present in the certificate
+                       ProcessCertificateExtensions (element);
+               }
+
+               private void WrapUp ()
+               {
+                       X509ChainElement element = elements [0];
+                       X509Certificate2 certificate = element.Certificate;
+
+                       // 6.1.5.a - TODO if certificate n (our 0) wasn't self issued and explicit_policy != 0
+                       if (IsSelfIssued (certificate)) {
+                               // TODO... decrement explicit_policy by 1
+                       }
+
+                       // 6.1.5.b - TODO
+
+                       // 6.1.5.c,d,e - not required by the X509Chain implementation
+
+                       // 6.1.5.f - recognize and process other critical extension present in the certificate
+                       ProcessCertificateExtensions (element);
+
+                       // 6.1.5.g - TODO
+
+                       // uncompressed the flags into several elements
+                       for (int i = elements.Count - 1; i >= 0; i--) {
+                               elements [i].UncompressFlags ();
+                       }
+               }
+
+               private void ProcessCertificateExtensions (X509ChainElement element)
+               {
+                       foreach (X509Extension ext in element.Certificate.Extensions) {
+                               if (ext.Critical) {
+                                       switch (ext.Oid.Value) {
+                                       case "2.5.29.15": // X509KeyUsageExtension
+                                       case "2.5.29.19": // X509BasicConstraintsExtension
+                                               // we processed this extension
+                                               break;
+                                       default:
+                                               // note: Under Windows XP MS implementation seems to ignore 
+                                               // certificate with unknown critical extensions.
+                                               element.StatusFlags |= X509ChainStatusFlags.InvalidExtension;
+                                               break;
+                                       }
+                               }
+                       }
+               }
+
+               private bool IsSignedWith (X509Certificate2 signed, AsymmetricAlgorithm pubkey)
+               {
+                       if (pubkey == null)
+                               return false;
+                       // Sadly X509Certificate2 doesn't expose the signature nor the tbs (to be signed) structure
+                       MX.X509Certificate mx = signed.MonoCertificate;
+                       return (mx.VerifySignature (pubkey));
+               }
+
+               private string GetSubjectKeyIdentifier (X509Certificate2 certificate)
+               {
+                       X509SubjectKeyIdentifierExtension ski = (certificate.Extensions["2.5.29.14"] as X509SubjectKeyIdentifierExtension);
+                       return (ski == null) ? String.Empty : ski.SubjectKeyIdentifier;
+               }
+
+               // System.dll v2 doesn't have a class to deal with the AuthorityKeyIdentifier extension
+               static string GetAuthorityKeyIdentifier (X509Certificate2 certificate)
+               {
+                       return GetAuthorityKeyIdentifier (certificate.MonoCertificate.Extensions ["2.5.29.35"]);
+               }
+
+               // but anyway System.dll v2 doesn't expose CRL in any way so...
+               static string GetAuthorityKeyIdentifier (MX.X509Crl crl)
+               {
+                       return GetAuthorityKeyIdentifier (crl.Extensions ["2.5.29.35"]);
+               }
+
+               static string GetAuthorityKeyIdentifier (MX.X509Extension ext)
+               {
+                       if (ext == null)
+                               return String.Empty;
+                       MX.Extensions.AuthorityKeyIdentifierExtension aki = new MX.Extensions.AuthorityKeyIdentifierExtension (ext);
+                       byte[] id = aki.Identifier;
+                       if (id == null) 
+                               return String.Empty;
+                       StringBuilder sb = new StringBuilder ();
+                       foreach (byte b in id)
+                               sb.Append (b.ToString ("X02"));
+                       return sb.ToString ();
+               }
+
+               // we check the revocation only once we have built the complete chain
+               private void CheckRevocationOnChain (X509ChainStatusFlags flag)
+               {
+                       bool partial = ((flag & X509ChainStatusFlags.PartialChain) != 0);
+                       bool online;
+
+                       switch (ChainPolicy.RevocationMode) {
+                       case X509RevocationMode.Online:
+                               // default
+                               online = true;
+                               break;
+                       case X509RevocationMode.Offline:
+                               online = false;
+                               break;
+                       case X509RevocationMode.NoCheck:
+                               return;
+                       default:
+                               throw new InvalidOperationException (Locale.GetText ("Invalid revocation mode."));
+                       }
+
+                       bool unknown = partial;
+                       // from the root down to the end-entity
+                       for (int i = elements.Count - 1; i >= 0; i--) {
+                               bool check = true;
+
+                               switch (ChainPolicy.RevocationFlag) {
+                               case X509RevocationFlag.EndCertificateOnly:
+                                       check = (i == 0);
+                                       break;
+                               case X509RevocationFlag.EntireChain:
+                                       check = true;
+                                       break;
+                               case X509RevocationFlag.ExcludeRoot:
+                                       // default
+                                       check = (i != (elements.Count - 1));
+                                       // anyway, who's gonna sign that the root is invalid ?
+                                       break;
+                               }
+
+                               X509ChainElement element = elements [i];
+
+                               // we can't assume the revocation status if the certificate is bad (e.g. invalid signature)
+                               if (!unknown)
+                                       unknown |= ((element.StatusFlags & X509ChainStatusFlags.NotSignatureValid) != 0);
+
+                               if (unknown) {
+                                       // we can skip the revocation checks as we can't be sure of them anyway
+                                       element.StatusFlags |= X509ChainStatusFlags.RevocationStatusUnknown;
+                                       element.StatusFlags |= X509ChainStatusFlags.OfflineRevocation;
+                               } else if (check && !partial && !IsSelfIssued (element.Certificate)) {
+                                       // check for revocation (except for the trusted root and self-issued certs)
+                                       element.StatusFlags |= CheckRevocation (element.Certificate, i+1, online);
+                                       // if revoked, then all others following in the chain are unknown...
+                                       unknown |= ((element.StatusFlags & X509ChainStatusFlags.Revoked) != 0);
+                               }
+                       }
+               }
+
+               // This isn't how RFC3280 (section 6.3) deals with CRL, but then we don't (yet) support DP, deltas...
+               private X509ChainStatusFlags CheckRevocation (X509Certificate2 certificate, int ca, bool online)
+               {
+                       X509ChainStatusFlags result = X509ChainStatusFlags.RevocationStatusUnknown;
+                       X509ChainElement element = elements [ca];
+                       X509Certificate2 ca_cert = element.Certificate;
+
+                       // find the CRL from the "right" CA
+                       while (IsSelfIssued (ca_cert) && (ca < elements.Count - 1)) {
+                               // try with this self-issued
+                               result = CheckRevocation (certificate, ca_cert, online);
+                               if (result != X509ChainStatusFlags.RevocationStatusUnknown)
+                                       break;
+                               ca++;
+                               element = elements [ca];
+                               ca_cert = element.Certificate;
+                       }
+                       if (result == X509ChainStatusFlags.RevocationStatusUnknown)
+                               result = CheckRevocation (certificate, ca_cert, online);
+                       return result;
+               }
+
+               private X509ChainStatusFlags CheckRevocation (X509Certificate2 certificate, X509Certificate2 ca_cert, bool online)
+               {
+                       // change this if/when we support OCSP
+                       X509KeyUsageExtension kue = (ca_cert.Extensions["2.5.29.15"] as X509KeyUsageExtension);
+                       if (kue != null) {
+                               // ... verify CrlSign is set
+                               X509KeyUsageFlags success = X509KeyUsageFlags.CrlSign;
+                               if ((kue.KeyUsages & success) != success) {
+                                       // FIXME - we should try to find an alternative CA that has the CrlSign bit
+                                       return X509ChainStatusFlags.RevocationStatusUnknown;
+                               }
+                       }
+
+                       MX.X509Crl crl = FindCrl (ca_cert);
+
+                       if ((crl == null) && online) {
+                               // FIXME - download and install new CRL
+                               // then you get a second chance
+                               // crl = FindCrl (ca_cert, ref valid, ref out_of_date);
+
+                               // We need to get the subjectAltName and an URI from there (or use OCSP)        
+                               // X509KeyUsageExtension subjectAltName = (ca_cert.Extensions["2.5.29.17"] as X509KeyUsageExtension);
+                       }
+
+                       if (crl != null) {
+                               // validate the digital signature on the CRL using the CA public key
+                               // note #1: we can't use X509Crl.VerifySignature(X509Certificate) because it duplicates
+                               // checks and we loose the "why" of the failure
+                               // note #2: we do this before other tests as an invalid signature could be a hacked CRL
+                               // (so anything within can't be trusted)
+                               if (!crl.VerifySignature (ca_cert.PublicKey.Key)) {
+                                       return X509ChainStatusFlags.RevocationStatusUnknown;
+                               }
+
+                               MX.X509Crl.X509CrlEntry entry = crl.GetCrlEntry (certificate.MonoCertificate);
+                               if (entry != null) {
+                                       // We have an entry for this CRL that includes an unknown CRITICAL extension
+                                       // See [X.509 7.3] NOTE 4
+                                       if (!ProcessCrlEntryExtensions (entry))
+                                               return X509ChainStatusFlags.Revoked;
+
+                                       // FIXME - a little more is involved
+                                       if (entry.RevocationDate <= ChainPolicy.VerificationTime)
+                                               return X509ChainStatusFlags.Revoked;
+                               }
+
+                               // are we overdue for a CRL update ? if so we can't be sure of any certificate status
+                               if (crl.NextUpdate < ChainPolicy.VerificationTime)
+                                       return X509ChainStatusFlags.RevocationStatusUnknown | X509ChainStatusFlags.OfflineRevocation;
+
+                               // we have a CRL that includes an unknown CRITICAL extension
+                               // we put this check at the end so we do not "hide" any Revoked flags
+                               if (!ProcessCrlExtensions (crl)) {
+                                       return X509ChainStatusFlags.RevocationStatusUnknown;
+                               }
+                       } else {
+                               return X509ChainStatusFlags.RevocationStatusUnknown;
+                       }
+
+                       return X509ChainStatusFlags.NoError;
+               }
+
+               static MX.X509Crl CheckCrls (string subject, string ski, MX.X509Store store)
+               {
+                       if (store == null)
+                               return null;
+
+                       var crls = store.Crls;
+                       foreach (MX.X509Crl crl in crls) {
+                               if (crl.IssuerName == subject && (ski.Length == 0 || ski == GetAuthorityKeyIdentifier (crl)))
+                                       return crl;
+                       }
+                       return null; // No CRL found
+               }
+
+               private MX.X509Crl FindCrl (X509Certificate2 caCertificate)
+               {
+                       string subject = caCertificate.SubjectName.Decode (X500DistinguishedNameFlags.None);
+                       string ski = GetSubjectKeyIdentifier (caCertificate);
+
+                       // consider that the LocalMachine directories could not exists... and cannot be created by the user
+                       MX.X509Crl result = CheckCrls (subject, ski, LMCAStore.Store);
+                       if (result != null)
+                               return result;
+                       if (location == StoreLocation.CurrentUser) {
+                               result = CheckCrls (subject, ski, UserCAStore.Store);
+                               if (result != null)
+                                       return result;
+                       }
+
+                       // consider that the LocalMachine directories could not exists... and cannot be created by the user
+                       result = CheckCrls (subject, ski, LMRootStore.Store);
+                       if (result != null)
+                               return result;
+                       if (location == StoreLocation.CurrentUser) {
+                               result = CheckCrls (subject, ski, UserRootStore.Store);
+                               if (result != null)
+                                       return result;
+                       }
+                       return null;
+               }
+
+               private bool ProcessCrlExtensions (MX.X509Crl crl)
+               {
+                       foreach (MX.X509Extension ext in crl.Extensions) {
+                               if (ext.Critical) {
+                                       switch (ext.Oid) {
+                                       case "2.5.29.20": // cRLNumber
+                                       case "2.5.29.35": // authorityKeyIdentifier
+                                               // we processed/know about this extension
+                                               break;
+                                       default:
+                                               return false;
+                                       }
+                               }
+                       }
+                       return true;
+               }
+
+               private bool ProcessCrlEntryExtensions (MX.X509Crl.X509CrlEntry entry)
+               {
+                       foreach (MX.X509Extension ext in entry.Extensions) {
+                               if (ext.Critical) {
+                                       switch (ext.Oid) {
+                                       case "2.5.29.21": // cRLReason
+                                               // we processed/know about this extension
+                                               break;
+                                       default:
+                                               return false;
+                                       }
+                               }
+                       }
+                       return true;
+               }
+       }
+}
+#endif
diff --git a/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Helper2.cs b/mcs/class/System/System.Security.Cryptography.X509Certificates/X509Helper2.cs
new file mode 100644 (file)
index 0000000..2a9163a
--- /dev/null
@@ -0,0 +1,116 @@
+//
+// X509Helper2.cs
+//
+// Authors:
+//     Martin Baulig  <martin.baulig@xamarin.com>
+//
+// Copyright (C) 2016 Xamarin, Inc. (http://www.xamarin.com)
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+#if SECURITY_DEP
+#if MONO_SECURITY_ALIAS
+extern alias MonoSecurity;
+#endif
+
+#if MONO_SECURITY_ALIAS
+using MonoSecurity::Mono.Security.Interface;
+#else
+using Mono.Security.Interface;
+#endif
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       internal static class X509Helper2
+       {
+               internal static void Initialize ()
+               {
+                       X509Helper.InstallNativeHelper (new MyNativeHelper ());
+               }
+
+               internal static void ThrowIfContextInvalid (X509CertificateImpl impl)
+               {
+                       X509Helper.ThrowIfContextInvalid (impl);
+               }
+
+               internal static X509Certificate2Impl Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
+               {
+                       var provider = MonoTlsProviderFactory.GetProvider ();
+                       if (provider.HasNativeCertificates) {
+                               var impl = provider.GetNativeCertificate (rawData, password, keyStorageFlags);
+                               return impl;
+                       } else {
+                               var impl = new X509Certificate2ImplMono ();
+                               impl.Import (rawData, password, keyStorageFlags);
+                               return impl;
+                       }
+               }
+
+               internal static X509Certificate2Impl Import (X509Certificate cert)
+               {
+                       var provider = MonoTlsProviderFactory.GetProvider ();
+                       if (provider.HasNativeCertificates) {
+                               var impl = provider.GetNativeCertificate (cert);
+                               return impl;
+                       }
+                       var impl2 = cert.Impl as X509Certificate2Impl;
+                       if (impl2 != null)
+                               return (X509Certificate2Impl)impl2.Clone ();
+                       return Import (cert.GetRawCertData (), null, X509KeyStorageFlags.DefaultKeySet);
+               }
+
+               internal static X509ChainImpl CreateChainImpl (bool useMachineContext)
+               {
+                       return new X509ChainImplMono (useMachineContext);
+               }
+
+               public static bool IsValid (X509ChainImpl impl)
+               {
+                       return impl != null && impl.IsValid;
+               }
+
+               internal static void ThrowIfContextInvalid (X509ChainImpl impl)
+               {
+                       if (!IsValid (impl))
+                               throw GetInvalidChainContextException ();
+               }
+
+               internal static Exception GetInvalidChainContextException ()
+               {
+                       return new CryptographicException (Locale.GetText ("Chain instance is empty."));
+               }
+
+               class MyNativeHelper : INativeCertificateHelper
+               {
+                       public X509CertificateImpl Import (
+                               byte[] data, string password, X509KeyStorageFlags flags)
+                       {
+                               return X509Helper2.Import (data, password, flags);
+                       }
+
+                       public X509CertificateImpl Import (X509Certificate cert)
+                       {
+                               return X509Helper2.Import (cert);
+                       }
+               }
+       }
+}
+#endif
index 904142e3595e4737c60cddab3376e306953daa84..42b6c6e3d44dc65bdbf2d8838f498fdd51ed0c33 100644 (file)
@@ -40,7 +40,7 @@ using System.Security.Permissions;
 
 namespace System.Security.Cryptography.X509Certificates {
 
-       public sealed class X509Store : IDisposable {
+       public sealed class X509Store {
 
                private string _name;
                private StoreLocation _location;
@@ -107,10 +107,6 @@ namespace System.Security.Cryptography.X509Certificates {
                        _location = storeLocation;
                }
 
-               public void Dispose ()
-               {
-               }
-
                // properties
 
                public X509Certificate2Collection Certificates {
index e2c0718b8ab6f55f7f1581d43a55e380b5f8fe98..1d37b1294e573b833968429100e92c98aedcff57 100644 (file)
@@ -536,11 +536,15 @@ System.Security.Cryptography.X509Certificates/X509BasicConstraintsExtension.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2Collection.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2Enumerator.cs
+System.Security.Cryptography.X509Certificates/X509Certificate2Impl.cs
+System.Security.Cryptography.X509Certificates/X509Certificate2ImplMono.cs
 System.Security.Cryptography.X509Certificates/X509CertificateCollection.cs
 System.Security.Cryptography.X509Certificates/X509Chain.cs
 System.Security.Cryptography.X509Certificates/X509ChainElementCollection.cs
 System.Security.Cryptography.X509Certificates/X509ChainElement.cs
 System.Security.Cryptography.X509Certificates/X509ChainElementEnumerator.cs
+System.Security.Cryptography.X509Certificates/X509ChainImpl.cs
+System.Security.Cryptography.X509Certificates/X509ChainImplMono.cs
 System.Security.Cryptography.X509Certificates/X509ChainPolicy.cs
 System.Security.Cryptography.X509Certificates/X509ChainStatus.cs
 System.Security.Cryptography.X509Certificates/X509ChainStatusFlags.cs
@@ -550,6 +554,7 @@ System.Security.Cryptography.X509Certificates/X509Extension.cs
 System.Security.Cryptography.X509Certificates/X509ExtensionEnumerator.cs
 System.Security.Cryptography.X509Certificates/X509FindType.cs
 System.Security.Cryptography.X509Certificates/X509IncludeOption.cs
+System.Security.Cryptography.X509Certificates/X509Helper2.cs
 System.Security.Cryptography.X509Certificates/X509KeyUsageExtension.cs
 System.Security.Cryptography.X509Certificates/X509KeyUsageFlags.cs
 System.Security.Cryptography.X509Certificates/X509NameType.cs
index 715c748d1f5fe0cb703014e012db8fce842f0993..0638cb720b3a57d67b0879d93f72fce0a3bda685 100644 (file)
@@ -17,7 +17,7 @@ namespace MonoTests.System.Net.WebSockets
        [TestFixture]
        public class ClientWebSocketTest
        {
-               const string EchoServerUrl = "ws://echo.websocket.org";
+               const string EchoServerUrl = "ws://corefx-net.cloudapp.net/WebSocket/EchoWebSocket.ashx";
                int Port = NetworkHelpers.FindFreePort ();
                HttpListener listener;
                ClientWebSocket socket;
index 45649b8ad51a173ed0a658892fbf07fd0330042f..77fb73e3f00ed1404dbe81fe1a68294f5d7068a2 100644 (file)
@@ -81,13 +81,23 @@ namespace MonoTests.System.Net {
 
                public static MyNetworkStream CreateNS (int port)
                {
-                       return CreateNS (port, 5000);
+                       return CreateNS (IPAddress.Loopback, port, 5000);
                }
 
                public static MyNetworkStream CreateNS (int port, int timeout_ms)
+               {
+                       return CreateNS (IPAddress.Loopback, port, timeout_ms);
+               }
+
+               public static MyNetworkStream CreateNS (IPAddress ip, int port)
+               {
+                       return CreateNS (ip, port, 5000);
+               }
+
+               public static MyNetworkStream CreateNS (IPAddress ip, int port, int timeout_ms)
                {
                        Socket sock = new Socket (AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
-                       sock.Connect (new IPEndPoint (IPAddress.Loopback, port));
+                       sock.Connect (new IPEndPoint (ip, port));
                        sock.SendTimeout = timeout_ms;
                        sock.ReceiveTimeout = timeout_ms;
                        return new MyNetworkStream (sock);
index 06b756d387b2fae9ed04d69b2a44261ca8863c64..c088e4e14e2ddeb71509bbda356c4d7761d12c66 100644 (file)
@@ -32,6 +32,7 @@ using System.IO;
 using System.Net;
 using System.Net.Sockets;
 using System.Text;
+using System.Collections.Generic;
 
 using NUnit.Framework;
 
@@ -190,6 +191,26 @@ namespace MonoTests.System.Net
                        listener.Close ();
                }
 
+               [Test]
+               public void HttpRequestIsLocal ()
+               {
+                       var ips = new List<IPAddress> (Dns.GetHostAddresses (Dns.GetHostName ()));
+                       ips.Add (IPAddress.Loopback);
+                       foreach (var ip in ips) {
+                               if (ip.AddressFamily != AddressFamily.InterNetwork)
+                                       continue;
+
+                               HttpListener listener = HttpListener2Test.CreateAndStartListener (
+                                       "http://" + ip + ":9000/HttpRequestIsLocal/");
+                               NetworkStream ns = HttpListener2Test.CreateNS (ip, 9000);
+                               HttpListener2Test.Send (ns, "GET /HttpRequestIsLocal/ HTTP/1.0\r\n\r\n");
+                               HttpListenerContext ctx = listener.GetContext ();
+                               HttpListenerRequest request = ctx.Request;
+                               Assert.AreEqual (true, request.IsLocal, "IP " + ip + " is not local");
+                               listener.Close ();
+                       }
+               }
+
                [Test] // #29927
                public void HttpRequestUriUnescape ()
                {
index e642d688f3c59c8d62dd075b49ad48e36176f470..a7e48646d05dcf3b87af070d4ee4cb66ac045634 100644 (file)
@@ -1465,17 +1465,35 @@ WYpnKQqsKIzlSqv9wwXs7B1iA7ZdvHk3TAnSnLP1o2H7ME05UnZPKCvraONdezon
                }
 
                [Test]
-               [ExpectedException (typeof (ArgumentException))]
                public void GetNameInfo_Invalid_True ()
                {
-                       new X509Certificate2 ().GetNameInfo ((X509NameType) Int32.MinValue, true);
+                       try {
+                               // MS throws ArgumentException, Mono's new implementation throws
+                               // CryptographicException, which is consistent with other "certificate
+                               // instance is empty" situations.
+                               new X509Certificate2 ().GetNameInfo ((X509NameType) Int32.MinValue, true);
+                               Assert.Fail ("Expected exception.");
+                       } catch (ArgumentException) {
+                       } catch (CryptographicException) {
+                       } catch (Exception ex) {
+                               Assert.Fail ("Expected 'ArgumentException' or 'CryptographicException', got '{0}'", ex.GetType ());
+                       }
                }
 
                [Test]
-               [ExpectedException (typeof (ArgumentException))]
                public void GetNameInfo_Invalid_False ()
                {
-                       new X509Certificate2 ().GetNameInfo ((X509NameType) Int32.MinValue, false);
+                       try {
+                               // MS throws ArgumentException, Mono's new implementation throws
+                               // CryptographicException, which is consistent with other "certificate
+                               // instance is empty" situations.
+                               new X509Certificate2 ().GetNameInfo ((X509NameType) Int32.MinValue, false);
+                               Assert.Fail ("Expected exception.");
+                       } catch (ArgumentException) {
+                       } catch (CryptographicException) {
+                       } catch (Exception ex) {
+                               Assert.Fail ("Expected 'ArgumentException' or 'CryptographicException', got '{0}'", ex.GetType ());
+                       }
                }
 
                [Test]
@@ -1486,10 +1504,19 @@ WYpnKQqsKIzlSqv9wwXs7B1iA7ZdvHk3TAnSnLP1o2H7ME05UnZPKCvraONdezon
                }
 
                [Test]
-               [ExpectedException (typeof (NullReferenceException))]
                public void Empty_GetNameInfo_DnsName ()
                {
-                       new X509Certificate2 ().GetNameInfo (X509NameType.DnsName, true);
+                       try {
+                               // MS throws NullReferenceException, Mono's new implementation throws
+                               // CryptographicException, which is consistent with other "certificate
+                               // instance is empty" situations.
+                               new X509Certificate2 ().GetNameInfo (X509NameType.DnsName, true);
+                               Assert.Fail ("Expected exception.");
+                       } catch (NullReferenceException) {
+                       } catch (CryptographicException) {
+                       } catch (Exception ex) {
+                               Assert.Fail ("Expected 'NullReferenceException' or 'CryptographicException', got '{0}'", ex.GetType ());
+                       }
                }
 
                [Test]
index 42aae6ea158c8a8c299debefa02cc4bed9c01cd5..9fe0be90027bb9eb94769947fa80d510910e3281 100644 (file)
@@ -300,11 +300,15 @@ System.Security.Cryptography.X509Certificates/X509BasicConstraintsExtension.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2Collection.cs
 System.Security.Cryptography.X509Certificates/X509Certificate2Enumerator.cs
+System.Security.Cryptography.X509Certificates/X509Certificate2Impl.cs
+System.Security.Cryptography.X509Certificates/X509Certificate2ImplMono.cs
 System.Security.Cryptography.X509Certificates/X509CertificateCollection.cs
 System.Security.Cryptography.X509Certificates/X509Chain.cs
 System.Security.Cryptography.X509Certificates/X509ChainElement.cs
 System.Security.Cryptography.X509Certificates/X509ChainElementCollection.cs
 System.Security.Cryptography.X509Certificates/X509ChainElementEnumerator.cs
+System.Security.Cryptography.X509Certificates/X509ChainImpl.cs
+System.Security.Cryptography.X509Certificates/X509ChainImplMono.cs
 System.Security.Cryptography.X509Certificates/X509ChainPolicy.cs
 System.Security.Cryptography.X509Certificates/X509ChainStatus.cs
 System.Security.Cryptography.X509Certificates/X509ChainStatusFlags.cs
@@ -314,6 +318,7 @@ System.Security.Cryptography.X509Certificates/X509ExtensionCollection.cs
 System.Security.Cryptography.X509Certificates/X509ExtensionEnumerator.cs
 System.Security.Cryptography.X509Certificates/X509FindType.cs
 System.Security.Cryptography.X509Certificates/X509IncludeOption.cs
+System.Security.Cryptography.X509Certificates/X509Helper2.cs
 System.Security.Cryptography.X509Certificates/X509KeyUsageExtension.cs
 System.Security.Cryptography.X509Certificates/X509KeyUsageFlags.cs
 System.Security.Cryptography.X509Certificates/X509NameType.cs
index 8dce31d234c5b119f6502c1b4dbf3c9b3baf94c0..8f3de2eff5d4afd0a8048ca3c1460423b79e1ec6 100644 (file)
@@ -1,2 +1,5 @@
 #include mobile_System.dll.sources
 MonoTouch/MonoPInvokeCallbackAttribute.cs
+Assembly/AssemblyInfoEx.cs
+Mono.Net.Security/MonoTlsProviderFactoryExt.cs
+Mono.Security.Interface/MonoTlsProviderFactoryExt.cs
diff --git a/mcs/class/System/monotouch_opt_System.dll.sources b/mcs/class/System/monotouch_opt_System.dll.sources
deleted file mode 100644 (file)
index 6877457..0000000
+++ /dev/null
@@ -1 +0,0 @@
-Mono.Net.Security/MonoTlsProviderFactory.MonoTouch.opt.cs
diff --git a/mcs/class/System/monotouch_runtime_opt_System.dll.sources b/mcs/class/System/monotouch_runtime_opt_System.dll.sources
deleted file mode 100644 (file)
index 54025c5..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_System.dll.sources
diff --git a/mcs/class/System/monotouch_tv_opt_System.dll.sources b/mcs/class/System/monotouch_tv_opt_System.dll.sources
deleted file mode 100644 (file)
index 54025c5..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_System.dll.sources
diff --git a/mcs/class/System/monotouch_tv_runtime_opt_System.dll.sources b/mcs/class/System/monotouch_tv_runtime_opt_System.dll.sources
deleted file mode 100644 (file)
index 54025c5..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_System.dll.sources
diff --git a/mcs/class/System/monotouch_watch_opt_System.dll.sources b/mcs/class/System/monotouch_watch_opt_System.dll.sources
deleted file mode 100644 (file)
index 54025c5..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_System.dll.sources
diff --git a/mcs/class/System/monotouch_watch_runtime_opt_System.dll.sources b/mcs/class/System/monotouch_watch_runtime_opt_System.dll.sources
deleted file mode 100644 (file)
index 54025c5..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_System.dll.sources
index 70a77a6dbff401e4d973b5d5f8ce11321a969f9a..330f5106870020aee431722048cc1f9f8e8a4ba5 100644 (file)
@@ -1 +1,4 @@
 #include mobile_System.dll.sources
+Assembly/AssemblyInfoEx.cs
+Mono.Net.Security/MonoTlsProviderFactoryExt.cs
+Mono.Security.Interface/MonoTlsProviderFactoryExt.cs
index 3ff0aad1cfbd9e7ccb83c6ef390899c0cf041fe2..7e48f7ecc9d76cd28f42010171c2275d41b2d00f 100644 (file)
@@ -1 +1,2 @@
 #include System.dll.sources
+Assembly/AssemblyInfoEx.cs
diff --git a/mcs/class/System/xammac_net_4_5_opt_System.dll.sources b/mcs/class/System/xammac_net_4_5_opt_System.dll.sources
deleted file mode 100644 (file)
index 86ff246..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include xammac_opt_System.dll.sources
diff --git a/mcs/class/System/xammac_opt_System.dll.sources b/mcs/class/System/xammac_opt_System.dll.sources
deleted file mode 100644 (file)
index 6877457..0000000
+++ /dev/null
@@ -1 +0,0 @@
-Mono.Net.Security/MonoTlsProviderFactory.MonoTouch.opt.cs
index 476d3be7c22a21f834b329fd99a54215c312f005..2ee3b170c48f98baddbe1cbbb1e54337f9332648 100644 (file)
@@ -5,7 +5,8 @@ include ../../build/rules.make
 LIBRARY = WebMatrix.Data.dll
 
 LIB_REFS = System System.Data System.Core System.Configuration
-LIB_MCS_FLAGS = -r:$(corlib)
-TEST_MCS_FLAGS = -r:System.dll -r:System.Core.dll -r:System.Data.dll -r:Mono.Data.Sqlite.dll -r:Microsoft.CSharp.dll
+LIB_MCS_FLAGS =
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Core System.Data Mono.Data.Sqlite Microsoft.CSharp
 
 include ../../build/library.make
index 172a501446ed8ef2cdff39eaa58e4ce4ab20906d..842c1ed0ebe00b59e48bc1392671abaa8d8fb563 100644 (file)
@@ -5,14 +5,15 @@ LIBRARY = WindowsBase.dll
 
 LIB_REFS = System System.Xml
 LIB_MCS_FLAGS = -unsafe
-TEST_MCS_FLAGS = -unsafe -r:WindowsBase.dll -r:System.dll -r:System.Xml.dll -r:System.Core.dll
+TEST_MCS_FLAGS = -unsafe
+TEST_LIB_REFS = WindowsBase System System.Xml System.Core
 
 ifeq (2.0, $(FRAMEWORK_VERSION))
 LIB_MCS_FLAGS += -d:NET_3_0
 endif
 ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
 LIB_REFS += System.Xaml
-TEST_MCS_FLAGS += -r:System.Xaml.dll
+TEST_LIB_REFS += System.Xaml
 endif
 
 include ../../build/library.make
index 78f1d450916ebcef407256b2c6c0e626b17d08e6..4d0245c3746575153ead243e9585a895028811ae 100644 (file)
@@ -36,12 +36,12 @@ namespace System.Windows.Media {
        [ValueSerializer (typeof (MatrixValueSerializer))]
        public struct Matrix : IFormattable {
 
-               double m11;
-               double m12;
-               double m21;
-               double m22;
-               double offsetX;
-               double offsetY;
+               double _m11;
+               double _m12;
+               double _m21;
+               double _m22;
+               double _offsetX;
+               double _offsetY;
 
                public Matrix (double m11,
                               double m12,
@@ -50,12 +50,12 @@ namespace System.Windows.Media {
                               double offsetX,
                               double offsetY)
                {
-                       this.m11 = m11;
-                       this.m12 = m12;
-                       this.m21 = m21;
-                       this.m22 = m22;
-                       this.offsetX = offsetX;
-                       this.offsetY = offsetY;
+                       this._m11 = m11;
+                       this._m12 = m12;
+                       this._m21 = m21;
+                       this._m22 = m22;
+                       this._offsetX = offsetX;
+                       this._offsetY = offsetY;
                }
 
                public void Append (Matrix matrix)
@@ -67,30 +67,30 @@ namespace System.Windows.Media {
                        double _offsetX;
                        double _offsetY;
 
-                       _m11 = m11 * matrix.M11 + m12 * matrix.M21;
-                       _m12 = m11 * matrix.M12 + m12 * matrix.M22;
-                       _m21 = m21 * matrix.M11 + m22 * matrix.M21;
-                       _m22 = m21 * matrix.M12 + m22 * matrix.M22;
+                       _m11 = this._m11 * matrix.M11 + this._m12 * matrix.M21;
+                       _m12 = this._m11 * matrix.M12 + this._m12 * matrix.M22;
+                       _m21 = this._m21 * matrix.M11 + this._m22 * matrix.M21;
+                       _m22 = this._m21 * matrix.M12 + this._m22 * matrix.M22;
 
-                       _offsetX = offsetX * matrix.M11 + offsetY * matrix.M21 + matrix.OffsetX;
-                       _offsetY = offsetX * matrix.M12 + offsetY * matrix.M22 + matrix.OffsetY;
+                       _offsetX = this._offsetX * matrix.M11 + this._offsetY * matrix.M21 + matrix.OffsetX;
+                       _offsetY = this._offsetX * matrix.M12 + this._offsetY * matrix.M22 + matrix.OffsetY;
 
-                       m11 = _m11;
-                       m12 = _m12;
-                       m21 = _m21;
-                       m22 = _m22;
-                       offsetX = _offsetX;
-                       offsetY = _offsetY;
+                       this._m11 = _m11;
+                       this._m12 = _m12;
+                       this._m21 = _m21;
+                       this._m22 = _m22;
+                       this._offsetX = _offsetX;
+                       this._offsetY = _offsetY;
                }
 
                public bool Equals (Matrix value)
                {
-                       return (m11 == value.M11 &&
-                               m12 == value.M12 &&
-                               m21 == value.M21 &&
-                               m22 == value.M22 &&
-                               offsetX == value.OffsetX &&
-                               offsetY == value.OffsetY);
+                       return (_m11 == value.M11 &&
+                               _m12 == value.M12 &&
+                               _m21 == value.M21 &&
+                               _m22 == value.M22 &&
+                               _offsetX == value.OffsetX &&
+                               _offsetY == value.OffsetY);
                }
 
                public override bool Equals (object o)
@@ -121,20 +121,20 @@ namespace System.Windows.Media {
 
                        /* 1/(ad-bc)[d -b; -c a] */
 
-                       double _m11 = m22;
-                       double _m12 = -m12;
-                       double _m21 = -m21;
-                       double _m22 = m11;
+                       double _m11 = this._m22;
+                       double _m12 = -this._m12;
+                       double _m21 = -this._m21;
+                       double _m22 = this._m11;
 
-                       double _offsetX = m21 * offsetY - m22 * offsetX;
-                       double _offsetY = m12 * offsetX - m11 * offsetY;
+                       double _offsetX = this._m21 * this._offsetY - this._m22 * this._offsetX;
+                       double _offsetY = this._m12 * this._offsetX - this._m11 * this._offsetY;
 
-                       m11 = _m11 / d;
-                       m12 = _m12 / d;
-                       m21 = _m21 / d;
-                       m22 = _m22 / d;
-                       offsetX = _offsetX / d;
-                       offsetY = _offsetY / d;
+                       this._m11 = _m11 / d;
+                       this._m12 = _m12 / d;
+                       this._m21 = _m21 / d;
+                       this._m22 = _m22 / d;
+                       this._offsetX = _offsetX / d;
+                       this._offsetY = _offsetY / d;
                }
 
                public static Matrix Multiply (Matrix trans1,
@@ -179,20 +179,20 @@ namespace System.Windows.Media {
                        double _offsetX;
                        double _offsetY;
 
-                       _m11 = matrix.M11 * m11 + matrix.M12 * m21;
-                       _m12 = matrix.M11 * m12 + matrix.M12 * m22;
-                       _m21 = matrix.M21 * m11 + matrix.M22 * m21;
-                       _m22 = matrix.M21 * m12 + matrix.M22 * m22;
+                       _m11 = matrix.M11 * this._m11 + matrix.M12 * this._m21;
+                       _m12 = matrix.M11 * this._m12 + matrix.M12 * this._m22;
+                       _m21 = matrix.M21 * this._m11 + matrix.M22 * this._m21;
+                       _m22 = matrix.M21 * this._m12 + matrix.M22 * this._m22;
 
-                       _offsetX = matrix.OffsetX * m11 + matrix.OffsetY * m21 + offsetX;
-                       _offsetY = matrix.OffsetX * m12 + matrix.OffsetY * m22 + offsetY;
+                       _offsetX = matrix.OffsetX * this._m11 + matrix.OffsetY * this._m21 + this._offsetX;
+                       _offsetY = matrix.OffsetX * this._m12 + matrix.OffsetY * this._m22 + this._offsetY;
 
-                       m11 = _m11;
-                       m12 = _m12;
-                       m21 = _m21;
-                       m22 = _m22;
-                       offsetX = _offsetX;
-                       offsetY = _offsetY;
+                       this._m11 = _m11;
+                       this._m12 = _m12;
+                       this._m21 = _m21;
+                       this._m22 = _m22;
+                       this._offsetX = _offsetX;
+                       this._offsetY = _offsetY;
                }
 
                public void Rotate (double angle)
@@ -272,9 +272,9 @@ namespace System.Windows.Media {
 
                public void SetIdentity ()
                {
-                       m11 = m22 = 1.0;
-                       m12 = m21 = 0.0;
-                       offsetX = offsetY = 0.0;
+                       _m11 = _m22 = 1.0;
+                       _m12 = _m21 = 0.0;
+                       _offsetX = _offsetY = 0.0;
                }
 
                public void Skew (double skewX,
@@ -306,7 +306,7 @@ namespace System.Windows.Media {
                                return "Identity";
                        else
                                return string.Format ("{0},{1},{2},{3},{4},{5}",
-                                                     m11, m12, m21, m22, offsetX, offsetY);
+                                                     _m11, _m12, _m21, _m22, _offsetX, _offsetY);
                }
 
                public string ToString (IFormatProvider provider)
@@ -339,8 +339,8 @@ namespace System.Windows.Media {
                public void Translate (double offsetX,
                                       double offsetY)
                {
-                       this.offsetX += offsetX;
-                       this.offsetY += offsetY;
+                       this._offsetX += offsetX;
+                       this._offsetY += offsetY;
                }
 
                public void TranslatePrepend (double offsetX,
@@ -352,7 +352,7 @@ namespace System.Windows.Media {
                }
 
                public double Determinant {
-                       get { return m11 * m22 - m12 * m21; }
+                       get { return _m11 * _m22 - _m12 * _m21; }
                }
 
                public bool HasInverse {
@@ -368,28 +368,28 @@ namespace System.Windows.Media {
                }
 
                public double M11 { 
-                       get { return m11; }
-                       set { m11 = value; }
+                       get { return _m11; }
+                       set { _m11 = value; }
                }
                public double M12 { 
-                       get { return m12; }
-                       set { m12 = value; }
+                       get { return _m12; }
+                       set { _m12 = value; }
                }
                public double M21 { 
-                       get { return m21; }
-                       set { m21 = value; }
+                       get { return _m21; }
+                       set { _m21 = value; }
                }
                public double M22 { 
-                       get { return m22; }
-                       set { m22 = value; }
+                       get { return _m22; }
+                       set { _m22 = value; }
                }
                public double OffsetX { 
-                       get { return offsetX; }
-                       set { offsetX = value; }
+                       get { return _offsetX; }
+                       set { _offsetX = value; }
                }
                public double OffsetY { 
-                       get { return offsetY; }
-                       set { offsetY = value; }
+                       get { return _offsetY; }
+                       set { _offsetY = value; }
                }
        }
 
index 9c014ddf5625c1ba8803a6b9a0dc5bcab6c39470..f2b464be1e5b68808a2d0b9f6168842dae539650 100644 (file)
@@ -38,14 +38,14 @@ namespace System.Windows {
        [ValueSerializer (typeof(Int32RectValueSerializer))]
        public struct Int32Rect : IFormattable
        {
-               int x, y, width, height;
+               int _x, _y, _width, _height;
 
                public Int32Rect (int x, int y, int width, int height)
                {
-                       this.x = x;
-                       this.y = y;
-                       this.width = width;
-                       this.height = height;
+                       this._x = x;
+                       this._y = y;
+                       this._width = width;
+                       this._height = height;
                }
 
                public static bool operator != (Int32Rect int32Rect1, Int32Rect int32Rect2)
@@ -63,35 +63,35 @@ namespace System.Windows {
                }
 
                public int Height {
-                       get { return height; }
-                       set { height = value; }
+                       get { return _height; }
+                       set { _height = value; }
                }
 
                public bool IsEmpty {
-                       get { return width == 0 && height == 0; }
+                       get { return _width == 0 && _height == 0; }
                }
 
                public int Width {
-                       get { return width; }
-                       set { width = value; }
+                       get { return _width; }
+                       set { _width = value; }
                }
 
                public int X {
-                       get { return x; }
-                       set { x = value; }
+                       get { return _x; }
+                       set { _x = value; }
                }
 
                public int Y {
-                       get { return y; }
-                       set { y = value; }
+                       get { return _y; }
+                       set { _y = value; }
                }
 
                public bool Equals (Int32Rect value)
                {
-                       return (x == value.x &&
-                               y == value.y &&
-                               width == value.width &&
-                               height == value.height);
+                       return (_x == value._x &&
+                               _y == value._y &&
+                               _width == value._width &&
+                               _height == value._height);
                }
 
                public override bool Equals (object o)
@@ -121,7 +121,7 @@ namespace System.Windows {
                {
                        if (IsEmpty)
                                return "Empty";
-                       return String.Format ("{0},{1},{2},{3}", x, y, width, height);
+                       return String.Format ("{0},{1},{2},{3}", _x, _y, _width, _height);
                }
 
                public string ToString (IFormatProvider provider)
index e5296c6f1d8e141969d3efa65bb16f2f43d52466..206b0edd3ab7302b161d03cd78e98c01758da003 100644 (file)
@@ -39,18 +39,18 @@ namespace System.Windows {
        {
                public Point (double x, double y)
                {
-                       this.x = x;
-                       this.y = y;
+                       this._x = x;
+                       this._y = y;
                }
 
                public double X {
-                       get { return x; }
-                       set { x = value; }
+                       get { return _x; }
+                       set { _x = value; }
                }
 
                public double Y {
-                       get { return y; }
-                       set { y = value; }
+                       get { return _y; }
+                       set { _y = value; }
                }
 
                public override bool Equals (object o)
@@ -62,19 +62,19 @@ namespace System.Windows {
 
                public bool Equals (Point value)
                {
-                       return x == value.X && y == value.Y;
+                       return _x == value.X && _y == value.Y;
                }
 
                public override int GetHashCode ()
                {
-                   return (x.GetHashCode() ^ y.GetHashCode());
+                   return (_x.GetHashCode() ^ _y.GetHashCode());
                }
 
 
                public void Offset (double offsetX, double offsetY)
                {
-                       x += offsetX;
-                       y += offsetY;
+                       _x += offsetX;
+                       _y += offsetY;
                }
 
                public static Point Add (Point point, Vector vector)
@@ -179,7 +179,7 @@ namespace System.Windows {
                                seperator = ";";
                        else
                                seperator = ",";
-                       object[] ob = { this.x, seperator, this.y };
+                       object[] ob = { this._x, seperator, this._y };
 
                        return string.Format(formatProvider, "{0:" + format + "}{1}{2:" + format + "}", ob);
                }
@@ -189,7 +189,7 @@ namespace System.Windows {
                        return this.ToString(format, formatProvider);
                }
 
-               double x;
-               double y;
+               double _x;
+               double _y;
        }
 }
index 2c5f3c0e6192b5dd5d9a6464fec52bb8206b4687..fd38ec6c25ed169cbff90534070b583eb93b99be 100644 (file)
@@ -41,9 +41,9 @@ namespace System.Windows {
        {
                public Rect (Size size)
                {
-                       x = y = 0.0;
-                       width = size.Width;
-                       height = size.Height;
+                       _x = _y = 0.0;
+                       _width = size.Width;
+                       _height = size.Height;
                }
 
                public Rect (Point point, Vector vector) : this (point, Point.Add (point, vector))
@@ -52,21 +52,21 @@ namespace System.Windows {
                public Rect (Point point1, Point point2)
                {
                        if (point1.X < point2.X) {
-                               x = point1.X;
-                               width = point2.X - point1.X;
+                               _x = point1.X;
+                               _width = point2.X - point1.X;
                        }
                        else {
-                               x = point2.X;
-                               width = point1.X - point2.X;
+                               _x = point2.X;
+                               _width = point1.X - point2.X;
                        }
 
                        if (point1.Y < point2.Y) {
-                               y = point1.Y;
-                               height = point2.Y - point1.Y;
+                               _y = point1.Y;
+                               _height = point2.Y - point1.Y;
                        }
                        else {
-                               y = point2.Y;
-                               height = point1.Y - point2.Y;
+                               _y = point2.Y;
+                               _height = point1.Y - point2.Y;
                        }
                }
 
@@ -74,26 +74,26 @@ namespace System.Windows {
                {
                        if (width < 0 || height < 0)
                                throw new ArgumentException ("width and height must be non-negative.");
-                       this.x = x;
-                       this.y = y;
-                       this.width = width;
-                       this.height = height;
+                       this._x = x;
+                       this._y = y;
+                       this._width = width;
+                       this._height = height;
                }
 
                public Rect (Point location, Size size)
                {
-                       x = location.X;
-                       y = location.Y;
-                       width = size.Width;
-                       height = size.Height;
+                       _x = location.X;
+                       _y = location.Y;
+                       _width = size.Width;
+                       _height = size.Height;
                }
 
                public bool Equals (Rect value)
                {
-                       return (x == value.X &&
-                               y == value.Y &&
-                               width == value.Width &&
-                               height == value.Height);
+                       return (_x == value.X &&
+                               _y == value.Y &&
+                               _width == value.Width &&
+                               _height == value.Height);
                }
 
                public static bool operator != (Rect rect1, Rect rect2)
@@ -172,11 +172,11 @@ namespace System.Windows {
                public void Inflate (double width, double height)
                {
                        // XXX any error checking like in the static case?
-                       x -= width;
-                       y -= height;
+                       _x -= width;
+                       _y -= height;
 
-                       this.width += 2*width;
-                       this.height += 2*height;
+                       this._width += 2*width;
+                       this._height += 2*height;
                }
 
                public void Inflate (Size size)
@@ -192,20 +192,20 @@ namespace System.Windows {
 
                public void Intersect(Rect rect)
                {
-                       double _x = Math.Max (x, rect.x);
-                       double _y = Math.Max (y, rect.y);
+                       double _x = Math.Max (this._x, rect._x);
+                       double _y = Math.Max (this._y, rect._y);
                        double _width = Math.Min (Right, rect.Right) - _x;
                        double _height = Math.Min (Bottom, rect.Bottom) - _y; 
 
                        if (_width < 0 || _height < 0) {
-                               x = y = Double.PositiveInfinity;
-                               width = height = Double.NegativeInfinity;
+                               this._x = this._y = Double.PositiveInfinity;
+                               this._width = this._height = Double.NegativeInfinity;
                        }
                        else {
-                               x = _x;
-                               y = _y;
-                               width = _width;
-                               height = _height;
+                               this._x = _x;
+                               this._y = _y;
+                               this._width = _width;
+                               this._height = _height;
                        }
                }
 
@@ -218,8 +218,8 @@ namespace System.Windows {
 
                public void Offset(double offsetX, double offsetY)
                {
-                       x += offsetX;
-                       y += offsetY;
+                       _x += offsetX;
+                       _y += offsetY;
                }
 
                public static Rect Offset(Rect rect, double offsetX, double offsetY)
@@ -231,8 +231,8 @@ namespace System.Windows {
 
                public void Offset (Vector offsetVector)
                {
-                       x += offsetVector.X;
-                       y += offsetVector.Y;
+                       _x += offsetVector.X;
+                       _y += offsetVector.Y;
                }
 
                public static Rect Offset (Rect rect, Vector offsetVector)
@@ -244,10 +244,10 @@ namespace System.Windows {
 
                public void Scale(double scaleX, double scaleY)
                {
-                       x *= scaleX;
-                       y *= scaleY;
-                       width *= scaleX;
-                       height *= scaleY;
+                       _x *= scaleX;
+                       _y *= scaleY;
+                       _width *= scaleX;
+                       _height *= scaleY;
                }
 
                public void Transform (Matrix matrix)
@@ -283,10 +283,10 @@ namespace System.Windows {
                        var right = Math.Max (Right, rect.Right);
                        var bottom = Math.Max (Bottom, rect.Bottom);
                        
-                       x = left;
-                       y = top;
-                       width = right - left;
-                       height = bottom - top;
+                       _x = left;
+                       _y = top;
+                       _width = right - left;
+                       _height = bottom - top;
                }
 
                public void Union(Point point)
@@ -336,37 +336,37 @@ namespace System.Windows {
                                "{{0:{0}}}{1}{{1:{0}}}{1}{{2:{0}}}{1}{{3:{0}}}",
                                format, separator);
                        return String.Format (provider, rectFormat,
-                               x, y, width, height);
+                               _x, _y, _width, _height);
                }
 
                public static Rect Empty { 
                        get {
                                Rect r = new Rect ();
-                               r.x = r.y = Double.PositiveInfinity;
-                               r.width = r.height = Double.NegativeInfinity;
+                               r._x = r._y = Double.PositiveInfinity;
+                               r._width = r._height = Double.NegativeInfinity;
                                return r;
                        } 
                }
                
                public bool IsEmpty { 
                        get {
-                               return (x == Double.PositiveInfinity &&
-                                       y == Double.PositiveInfinity &&
-                                       width == Double.NegativeInfinity &&
-                                       height == Double.NegativeInfinity);
+                               return (_x == Double.PositiveInfinity &&
+                                       _y == Double.PositiveInfinity &&
+                                       _width == Double.NegativeInfinity &&
+                                       _height == Double.NegativeInfinity);
                        }
                }
                
                public Point Location { 
                        get {
-                               return new Point (x, y);
+                               return new Point (_x, _y);
                        }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
 
-                               x = value.X;
-                               y = value.Y;
+                               _x = value.X;
+                               _y = value.Y;
                        }
                }
                
@@ -374,39 +374,39 @@ namespace System.Windows {
                        get { 
                                if (IsEmpty)
                                        return Size.Empty; 
-                               return new Size (width, height);
+                               return new Size (_width, _height);
                        }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
 
-                               width = value.Width;
-                               height = value.Height;
+                               _width = value.Width;
+                               _height = value.Height;
                        }
                }
 
                public double X {
-                       get { return x; }
+                       get { return _x; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
 
-                               x = value;
+                               _x = value;
                        }
                }
 
                public double Y {
-                       get { return y; }
+                       get { return _y; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
 
-                               y = value;
+                               _y = value;
                        }
                }
 
                public double Width {
-                       get { return width; }
+                       get { return _width; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
@@ -414,12 +414,12 @@ namespace System.Windows {
                                if (value < 0)
                                        throw new ArgumentException ("width must be non-negative.");
 
-                               width = value;
+                               _width = value;
                        }
                }
 
                public double Height {
-                       get { return height; }
+                       get { return _height; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Rect.");
@@ -427,24 +427,24 @@ namespace System.Windows {
                                if (value < 0)
                                        throw new ArgumentException ("height must be non-negative.");
 
-                               height = value;
+                               _height = value;
                        }
                }
 
                public double Left { 
-                       get { return x; }
+                       get { return _x; }
                }
 
                public double Top { 
-                       get { return y; }
+                       get { return _y; }
                }
                
                public double Right { 
-                       get { return x + width; }
+                       get { return _x + _width; }
                }
                
                public double Bottom { 
-                       get { return y + height; }
+                       get { return _y + _height; }
                }
                
                public Point TopLeft { 
@@ -463,9 +463,9 @@ namespace System.Windows {
                        get { return new Point (Right, Bottom); }
                }
                
-               double x;
-               double y;
-               double width;
-               double height;
+               double _x;
+               double _y;
+               double _width;
+               double _height;
        }
 }
index 9e45b1a81d1f1199dcdb077998b6796e8ddac8db..729bfd07882a8243f40d72cd9517f2be109e017d 100644 (file)
@@ -40,13 +40,13 @@ namespace System.Windows {
                        if (width < 0 || height < 0)
                                throw new ArgumentException ("Width and Height must be non-negative.");
 
-                       this.width = width;
-                       this.height = height;
+                       this._width = width;
+                       this._height = height;
                }
 
                public bool Equals (Size value)
                {
-                       return width == value.Width && height == value.Height;
+                       return _width == value.Width && _height == value.Height;
                }
                
                public override bool Equals (object o)
@@ -76,7 +76,7 @@ namespace System.Windows {
                {
                        if (IsEmpty)
                                return "Empty";
-                       return String.Format ("{0},{1}", width, height);
+                       return String.Format ("{0},{1}", _width, _height);
                }
 
                public string ToString (IFormatProvider provider)
@@ -91,13 +91,13 @@ namespace System.Windows {
 
                public bool IsEmpty {
                        get {
-                               return (width == Double.NegativeInfinity &&
-                                       height == Double.NegativeInfinity);
+                               return (_width == Double.NegativeInfinity &&
+                                       _height == Double.NegativeInfinity);
                        }
                }
 
                public double Height {
-                       get { return height; }
+                       get { return _height; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Size.");
@@ -105,12 +105,12 @@ namespace System.Windows {
                                if (value < 0)
                                        throw new ArgumentException ("height must be non-negative.");
 
-                               height = value;
+                               _height = value;
                        }
                }
 
                public double Width {
-                       get { return width; }
+                       get { return _width; }
                        set {
                                if (IsEmpty)
                                        throw new InvalidOperationException ("Cannot modify this property on the Empty Size.");
@@ -118,14 +118,14 @@ namespace System.Windows {
                                if (value < 0)
                                        throw new ArgumentException ("width must be non-negative.");
 
-                               width = value;
+                               _width = value;
                        }
                }
 
                public static Size Empty {
                        get {
                                Size s = new Size ();
-                               s.width = s.height = Double.NegativeInfinity;
+                               s._width = s._height = Double.NegativeInfinity;
                                return s;
                        }
                }
@@ -151,7 +151,7 @@ namespace System.Windows {
                        return !size1.Equals (size2);
                }
 
-               double width;
-               double height;
+               double _width;
+               double _height;
        }
 }
index 794f6b8309c60a4c5ddd3bb62b5e665f7347f566..5ed53c3e249cbab2c7ca461a8082147f3b16218a 100644 (file)
@@ -38,13 +38,13 @@ namespace System.Windows {
        {
                public Vector (double x, double y)
                {
-                       this.x = x;
-                       this.y = y;
+                       this._x = x;
+                       this._y = y;
                }
 
                public bool Equals (Vector value)
                {
-                       return x == value.X && y == value.Y;
+                       return _x == value.X && _y == value.Y;
                }
 
                public override bool Equals (object o)
@@ -62,7 +62,7 @@ namespace System.Windows {
 
                string IFormattable.ToString (string format, IFormatProvider provider)
                {
-                       return string.Format (provider, "{0:" + format + "},{1:" + format + "}", x, y);
+                       return string.Format (provider, "{0:" + format + "},{1:" + format + "}", _x, _y);
                }
 
                public static bool Equals (Vector vector1, Vector vector2)
@@ -128,8 +128,8 @@ namespace System.Windows {
 
                public void Negate ()
                {
-                       x = -x;
-                       y = -y;
+                       _x = -_x;
+                       _y = -_y;
                }
 
                public void Normalize ()
@@ -139,8 +139,8 @@ namespace System.Windows {
                                return;
 
                        double l = Math.Sqrt (ls);
-                       x /= l;
-                       y /= l;
+                       _x /= l;
+                       _y /= l;
                }
 
                public static Vector Subtract (Vector vector1, Vector vector2)
@@ -155,7 +155,7 @@ namespace System.Windows {
 
                public override string ToString ()
                {
-                       return String.Format ("{0},{1}", x, y);
+                       return String.Format ("{0},{1}", _x, _y);
                }
 
                public string ToString (IFormatProvider provider)
@@ -168,17 +168,17 @@ namespace System.Windows {
                }
 
                public double LengthSquared {
-                       get { return x * x + y * y; }
+                       get { return _x * _x + _y * _y; }
                }
 
                public double X {
-                       get { return x; }
-                       set { x = value; }
+                       get { return _x; }
+                       set { _x = value; }
                }
 
                public double Y {
-                       get { return y; }
-                       set { y = value; }
+                       get { return _y; }
+                       set { _y = value; }
                }
 
                /* operators */
@@ -249,8 +249,8 @@ namespace System.Windows {
                        return Add (vector1, vector2);
                }
 
-               double x;
-               double y;
+               double _x;
+               double _y;
        }
 
 }
index cf95aee80ea0e92aa4eec92c3b2ce8c4a6bf8ccd..3c68cceb82bd865d74cc309f0221d75921bfc667 100644 (file)
@@ -94,4 +94,5 @@ using System.Runtime.InteropServices;
 [assembly: InternalsVisibleTo ("Xamarin.Mac, PublicKey=0024000004800000940000000602000000240000525341310004000011000000438ac2a5acfbf16cbd2b2b47a62762f273df9cb2795ceccdf77d10bf508e69e7a362ea7a45455bbf3ac955e1f2e2814f144e5d817efc4c6502cc012df310783348304e3ae38573c6d658c234025821fda87a0be8a0d504df564e2c93b2b878925f42503e9d54dfef9f9586d9e6f38a305769587b1de01f6c0410328b2c9733db")]
 #endif
 
+[assembly: InternalsVisibleTo ("Xamarin.BoringTls, PublicKey=002400000480000094000000060200000024000052534131000400001100000099dd12eda85767ae6f06023ee28e711c7e5a212462095c83868c29db75eddf6d8e296e03824c14fedd5f55553fed0b6173be3cc985a4b7f9fb7c83ccff8ba3938563b3d1f45a81122f12a1bcb73edcaad61a8456c7595a6da5184b4dd9d10f011b949ef1391fccfeab1ba62aa51c267ef8bd57ef1b6ba5a4c515d0badb81a78f")]
 [assembly: Guid ("BED7F4EA-1A96-11D2-8F08-00A0C9A6186D")]
diff --git a/mcs/class/corlib/CommonCrypto/.gitignore b/mcs/class/corlib/CommonCrypto/.gitignore
new file mode 100644 (file)
index 0000000..bd99fb0
--- /dev/null
@@ -0,0 +1 @@
+*.g.cs
diff --git a/mcs/class/corlib/CommonCrypto/CommonCrypto.cs b/mcs/class/corlib/CommonCrypto/CommonCrypto.cs
new file mode 100644 (file)
index 0000000..c765b95
--- /dev/null
@@ -0,0 +1,130 @@
+// CommonCrypto bindings for MonoMac and MonoTouch
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012-2014 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+using System.Runtime.InteropServices;
+
+namespace Crimson.CommonCrypto {
+
+       // int32_t -> CommonCryptor.h
+       enum CCCryptorStatus {
+           Success                     = 0,
+       ParamError              = -4300,
+           BufferTooSmall      = -4301,
+       MemoryFailure   = -4302,
+       AlignmentError  = -4303,
+       DecodeError             = -4304,
+       Unimplemented   = -4305
+       }
+       
+       // uint32_t -> CommonCryptor.h
+       // note: not exposed publicly so it can stay signed
+       enum CCOperation {
+               Encrypt = 0, 
+               Decrypt,     
+       }
+
+       // uint32_t -> CommonCryptor.h
+       // note: not exposed publicly so it can stay signed
+       enum CCAlgorithm {
+               AES128 = 0,
+               DES,        
+               TripleDES,       
+               CAST,       
+               RC4,
+               RC2,   
+               Blowfish    
+       }
+       
+       // uint32_t -> CommonCryptor.h
+       // note: not exposed publicly so it can stay signed
+       [Flags]
+       enum CCOptions {
+               None                    = 0,
+               PKCS7Padding    = 1,
+               ECBMode                 = 2
+       }
+       
+       static class Cryptor {
+               
+               const string libSystem = "/usr/lib/libSystem.dylib";
+               
+               // size_t was changed to IntPtr for 32/64 bits size difference - even if mono is (moslty) used in 32bits only on OSX today
+               // not using `nint` to be able to resue this outside (if needed)
+               
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorCreate (CCOperation op, CCAlgorithm alg, CCOptions options, /* const void* */ byte[] key, /* size_t */ IntPtr keyLength, /* const void* */ byte[] iv, /* CCCryptorRef* */ ref IntPtr cryptorRef);
+
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorRelease (/* CCCryptorRef */ IntPtr cryptorRef);
+
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorUpdate (/* CCCryptorRef */ IntPtr cryptorRef, /* const void* */ byte[] dataIn, /* size_t */ IntPtr dataInLength, /* void* */ byte[] dataOut, /* size_t */ IntPtr dataOutAvailable, /* size_t* */ ref IntPtr dataOutMoved);
+
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorUpdate (/* CCCryptorRef */ IntPtr cryptorRef, /* const void* */ IntPtr dataIn, /* size_t */ IntPtr dataInLength, /* void* */ IntPtr dataOut, /* size_t */ IntPtr dataOutAvailable, /* size_t* */ ref IntPtr dataOutMoved);
+
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorFinal (/* CCCryptorRef */ IntPtr cryptorRef, /* void* */ byte[] dataOut, /* size_t */ IntPtr dataOutAvailable, /* size_t* */ ref IntPtr dataOutMoved);
+
+               [DllImport (libSystem)]
+               extern internal static int CCCryptorGetOutputLength (/* CCCryptorRef */ IntPtr cryptorRef, /* size_t */ IntPtr inputLength, bool final);
+
+               [DllImport (libSystem)]
+               extern internal static CCCryptorStatus CCCryptorReset (/* CCCryptorRef */ IntPtr cryptorRef, /* const void* */ IntPtr iv);
+               
+               // helper method to reduce the amount of generate code for each cipher algorithm
+               static internal IntPtr Create (CCOperation operation, CCAlgorithm algorithm, CCOptions options, byte[] key, byte[] iv)
+               {
+                       if (key == null)
+                               throw new CryptographicException ("A null key was provided");
+                       
+                       // unlike the .NET framework CommonCrypto does not support two-keys triple-des (128 bits) ref: #6967
+                       if ((algorithm == CCAlgorithm.TripleDES) && (key.Length == 16)) {
+                               byte[] key3 = new byte [24];
+                               Buffer.BlockCopy (key, 0, key3, 0, 16);
+                               Buffer.BlockCopy (key, 0, key3, 16, 8);
+                               key = key3;
+                       }
+                       
+                       IntPtr cryptor = IntPtr.Zero;
+                       CCCryptorStatus status = Cryptor.CCCryptorCreate (operation, algorithm, options, key, (IntPtr) key.Length, iv, ref cryptor);
+                       if (status != CCCryptorStatus.Success)
+                               throw new CryptographicUnexpectedOperationException ();
+                       return cryptor;
+               }
+
+               // size_t was changed to IntPtr for 32/64 bits size difference - even if mono is (moslty) used in 32bits only on OSX today
+               [DllImport ("/System/Library/Frameworks/Security.framework/Security")]
+               extern internal static /* int */ int SecRandomCopyBytes (/* SecRandomRef */ IntPtr rnd, /* size_t */ IntPtr count, /* uint8_t* */ byte[] bytes);
+               
+               static internal void GetRandom (byte[] buffer)
+               {
+                       if (SecRandomCopyBytes (IntPtr.Zero, (IntPtr) buffer.Length, buffer) != 0)
+                               throw new CryptographicException (Marshal.GetLastWin32Error ()); // errno
+               }
+       }
+       
+#if !MONOTOUCH && !XAMMAC
+       static class KeyBuilder {
+               static public byte[] Key (int size) 
+               {
+                       byte[] buffer = new byte [size];
+                       Cryptor.GetRandom (buffer);
+                       return buffer;
+               }
+       
+               static public byte[] IV (int size) 
+               {
+                       byte[] buffer = new byte [size];
+                       Cryptor.GetRandom (buffer);
+                       return buffer;
+               }
+       }
+#endif
+}
diff --git a/mcs/class/corlib/CommonCrypto/CorlibExtras.cs b/mcs/class/corlib/CommonCrypto/CorlibExtras.cs
new file mode 100644 (file)
index 0000000..5bdc69a
--- /dev/null
@@ -0,0 +1,24 @@
+//
+// CorlibExtras.cs: additional stuff not provided by autogenerated code
+//
+// Authors:
+//     Sebastien Pouliot (sebastien@xamarun.com)
+//
+// Copyright (C) 2012 Xamarin Inc. All rights reserved.
+//
+
+namespace System.Security.Cryptography {
+       
+       // required to ensure compatibility with MS implementation
+       public sealed partial class RC2CryptoServiceProvider : RC2 {
+               
+               public override int EffectiveKeySize {
+                       get { return base.EffectiveKeySize; }
+                       set {
+                               if (value != KeySizeValue)
+                                       throw new CryptographicUnexpectedOperationException ("Effective key size must match key size for compatibility");
+                               base.EffectiveKeySize = value; 
+                       }
+               }
+       }
+}
diff --git a/mcs/class/corlib/CommonCrypto/CryptorTransform.cs b/mcs/class/corlib/CommonCrypto/CryptorTransform.cs
new file mode 100644 (file)
index 0000000..10ca6fa
--- /dev/null
@@ -0,0 +1,60 @@
+// ICryptoTransform implementation on top of CommonCrypto and SymmetricTransform
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+
+using Mono.Security.Cryptography;
+
+namespace Crimson.CommonCrypto {
+
+       class CryptorTransform : SymmetricTransform {
+               
+               IntPtr handle;
+               IntPtr handle_e;
+               bool encryption;
+               
+               public CryptorTransform (IntPtr cryptor, IntPtr special, SymmetricAlgorithm algo, bool encryption, byte[] iv)
+                       : base (algo, encryption, iv)
+               {
+                       handle = cryptor;
+                       // for CFB we need to encrypt data while decrypting
+                       handle_e = special;
+                       this.encryption = encryption;
+               }
+               
+               ~CryptorTransform ()
+               {
+                       Dispose (false);
+               }
+               
+               // PRO: doing this ensure all cipher modes and padding modes supported by .NET will be available with CommonCrypto (drop-in replacements)
+               // CON: doing this will only process one block at the time, so it's not ideal for performance, but still a lot better than managed
+               protected override void ECB (byte[] input, byte[] output)
+               {
+                       IntPtr len = IntPtr.Zero;
+                       CCCryptorStatus s = Cryptor.CCCryptorUpdate ((encrypt == encryption) ? handle : handle_e, 
+                               input, (IntPtr) input.Length, output, (IntPtr) output.Length, ref len);
+                       if (((int) len != output.Length) || (s != CCCryptorStatus.Success))
+                               throw new CryptographicUnexpectedOperationException (s.ToString ());
+               }
+               
+               protected override void Dispose (bool disposing)
+               {
+                       if (handle != IntPtr.Zero) {
+                               Cryptor.CCCryptorRelease (handle);
+                               handle = IntPtr.Zero;
+                       }
+                       if (handle_e != IntPtr.Zero) {
+                               Cryptor.CCCryptorRelease (handle_e);
+                               handle_e = IntPtr.Zero;
+                       }
+                       base.Dispose (disposing);
+                       GC.SuppressFinalize (this);
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/CommonCrypto/FastCryptorTransform.cs b/mcs/class/corlib/CommonCrypto/FastCryptorTransform.cs
new file mode 100644 (file)
index 0000000..9ff7a5a
--- /dev/null
@@ -0,0 +1,348 @@
+// Fast, multi-block, ICryptoTransform implementation on top of CommonCrypto
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+
+using Mono.Security.Cryptography;
+
+namespace Crimson.CommonCrypto {
+
+       unsafe class FastCryptorTransform : ICryptoTransform {
+               
+               IntPtr handle;
+               bool encrypt;
+               int BlockSizeByte;
+               byte[] workBuff;
+               bool lastBlock;
+               PaddingMode padding;
+               
+               public FastCryptorTransform (IntPtr cryptor, SymmetricAlgorithm algo, bool encryption, byte[] iv)
+               {
+                       BlockSizeByte = (algo.BlockSize >> 3);
+                       
+                       if (iv == null) {
+                               iv = KeyBuilder.IV (BlockSizeByte);
+                       } else if (iv.Length < BlockSizeByte) {
+                               string msg = String.Format ("IV is too small ({0} bytes), it should be {1} bytes long.",
+                                       iv.Length, BlockSizeByte);
+                               throw new CryptographicException (msg);
+                       }
+                       
+                       handle = cryptor;
+                       encrypt = encryption;
+                       padding = algo.Padding;
+                       // transform buffer
+                       workBuff = new byte [BlockSizeByte];
+               }
+               
+               ~FastCryptorTransform ()
+               {
+                       Dispose (false);
+               }
+               
+               public void Dispose ()
+               {
+                       Dispose (true);
+               }
+               
+               protected virtual void Dispose (bool disposing)
+               {
+                       if (handle != IntPtr.Zero) {
+                               Cryptor.CCCryptorRelease (handle);
+                               handle = IntPtr.Zero;
+                       }
+                       GC.SuppressFinalize (this);
+               }
+
+               public virtual bool CanTransformMultipleBlocks {
+                       get { return true; }
+               }
+
+               public virtual bool CanReuseTransform {
+                       get { return false; }
+               }
+
+               public virtual int InputBlockSize {
+                       get { return BlockSizeByte; }
+               }
+
+               public virtual int OutputBlockSize {
+                       get { return BlockSizeByte; }
+               }
+
+               int Transform (byte[] input, int inputOffset, byte[] output, int outputOffset, int length)
+               {
+                       IntPtr len = IntPtr.Zero;
+                       IntPtr in_len = (IntPtr) length;
+                       IntPtr out_len = (IntPtr) (output.Length - outputOffset);
+                       fixed (byte* inputBuffer = &input [0])
+                       fixed (byte* outputBuffer = &output [0]) {
+                               CCCryptorStatus s = Cryptor.CCCryptorUpdate (handle, (IntPtr) (inputBuffer + inputOffset), in_len, (IntPtr) (outputBuffer + outputOffset), out_len, ref len);
+                               if (s != CCCryptorStatus.Success)
+                                       throw new CryptographicException (s.ToString ());
+                       }
+                       return (int) len;
+               }
+
+               private void CheckInput (byte[] inputBuffer, int inputOffset, int inputCount)
+               {
+                       if (inputBuffer == null)
+                               throw new ArgumentNullException ("inputBuffer");
+                       if (inputOffset < 0)
+                               throw new ArgumentOutOfRangeException ("inputOffset", "< 0");
+                       if (inputCount < 0)
+                               throw new ArgumentOutOfRangeException ("inputCount", "< 0");
+                       // ordered to avoid possible integer overflow
+                       if (inputOffset > inputBuffer.Length - inputCount)
+                               throw new ArgumentException ("inputBuffer", "Overflow");
+               }
+
+               // this method may get called MANY times so this is the one to optimize
+               public virtual int TransformBlock (byte[] inputBuffer, int inputOffset, int inputCount, byte[] outputBuffer, int outputOffset) 
+               {
+                       CheckInput (inputBuffer, inputOffset, inputCount);
+                       // check output parameters
+                       if (outputBuffer == null)
+                               throw new ArgumentNullException ("outputBuffer");
+                       if (outputOffset < 0)
+                               throw new ArgumentOutOfRangeException ("outputOffset", "< 0");
+
+                       // ordered to avoid possible integer overflow
+                       int len = outputBuffer.Length - inputCount - outputOffset;
+                       if (!encrypt && (0 > len) && ((padding == PaddingMode.None) || (padding == PaddingMode.Zeros))) {
+                               throw new CryptographicException ("outputBuffer", "Overflow");
+                       } else if (KeepLastBlock) {
+                               if (0 > len + BlockSizeByte) {
+                                       throw new CryptographicException ("outputBuffer", "Overflow");
+                               }
+                       } else {
+                               if (0 > len) {
+                                       // there's a special case if this is the end of the decryption process
+                                       if (inputBuffer.Length - inputOffset - outputBuffer.Length == BlockSizeByte)
+                                               inputCount = outputBuffer.Length - outputOffset;
+                                       else
+                                               throw new CryptographicException ("outputBuffer", "Overflow");
+                               }
+                       }
+                       return InternalTransformBlock (inputBuffer, inputOffset, inputCount, outputBuffer, outputOffset);
+               }
+
+               private bool KeepLastBlock {
+                       get {
+                               return ((!encrypt) && (padding != PaddingMode.None) && (padding != PaddingMode.Zeros));
+                       }
+               }
+
+               private int InternalTransformBlock (byte[] inputBuffer, int inputOffset, int inputCount, byte[] outputBuffer, int outputOffset) 
+               {
+                       int offs = inputOffset;
+                       int full;
+
+                       // this way we don't do a modulo every time we're called
+                       // and we may save a division
+                       if (inputCount != BlockSizeByte) {
+                               if ((inputCount % BlockSizeByte) != 0)
+                                       throw new CryptographicException ("Invalid input block size.");
+
+                               full = inputCount / BlockSizeByte;
+                       } else
+                               full = 1;
+
+                       if (KeepLastBlock)
+                               full--;
+
+                       int total = 0;
+
+                       if (lastBlock) {
+                               Transform (workBuff, 0, outputBuffer, outputOffset, BlockSizeByte);
+                               outputOffset += BlockSizeByte;
+                               total += BlockSizeByte;
+                               lastBlock = false;
+                       }
+
+                       if (full > 0) {
+                               int length = full * BlockSizeByte;
+                               Transform (inputBuffer, offs, outputBuffer, outputOffset, length);
+                               offs += length;
+                               outputOffset += length;
+                               total += length;
+                       }
+
+                       if (KeepLastBlock) {
+                               Buffer.BlockCopy (inputBuffer, offs, workBuff, 0, BlockSizeByte);
+                               lastBlock = true;
+                       }
+
+                       return total;
+               }
+
+               private void Random (byte[] buffer, int start, int length)
+               {
+                       byte[] random = new byte [length];
+                       Cryptor.GetRandom (random);
+                       Buffer.BlockCopy (random, 0, buffer, start, length);
+               }
+
+               private void ThrowBadPaddingException (PaddingMode padding, int length, int position)
+               {
+                       string msg = String.Format ("Bad {0} padding.", padding);
+                       if (length >= 0)
+                               msg += String.Format (" Invalid length {0}.", length);
+                       if (position >= 0)
+                               msg += String.Format (" Error found at position {0}.", position);
+                       throw new CryptographicException (msg);
+               }
+
+               private byte[] FinalEncrypt (byte[] inputBuffer, int inputOffset, int inputCount) 
+               {
+                       // are there still full block to process ?
+                       int full = (inputCount / BlockSizeByte) * BlockSizeByte;
+                       int rem = inputCount - full;
+                       int total = full;
+
+                       switch (padding) {
+                       case PaddingMode.ANSIX923:
+                       case PaddingMode.ISO10126:
+                       case PaddingMode.PKCS7:
+                               // we need to add an extra block for padding
+                               total += BlockSizeByte;
+                               break;
+                       default:
+                               if (inputCount == 0)
+                                       return new byte [0];
+                               if (rem != 0) {
+                                       if (padding == PaddingMode.None)
+                                               throw new CryptographicException ("invalid block length");
+                                       // zero padding the input (by adding a block for the partial data)
+                                       byte[] paddedInput = new byte [full + BlockSizeByte];
+                                       Buffer.BlockCopy (inputBuffer, inputOffset, paddedInput, 0, inputCount);
+                                       inputBuffer = paddedInput;
+                                       inputOffset = 0;
+                                       inputCount = paddedInput.Length;
+                                       total = inputCount;
+                               }
+                               break;
+                       }
+
+                       byte[] res = new byte [total];
+                       int outputOffset = 0;
+
+                       // process all blocks except the last (final) block
+                       if (total > BlockSizeByte) {
+                               outputOffset = InternalTransformBlock (inputBuffer, inputOffset, total - BlockSizeByte, res, 0);
+                               inputOffset += outputOffset;
+                       }
+
+                       // now we only have a single last block to encrypt
+                       byte pad = (byte) (BlockSizeByte - rem);
+                       switch (padding) {
+                       case PaddingMode.ANSIX923:
+                               // XX 00 00 00 00 00 00 07 (zero + padding length)
+                               res [res.Length - 1] = pad;
+                               Buffer.BlockCopy (inputBuffer, inputOffset, res, full, rem);
+                               // the last padded block will be transformed in-place
+                               InternalTransformBlock (res, full, BlockSizeByte, res, full);
+                               break;
+                       case PaddingMode.ISO10126:
+                               // XX 3F 52 2A 81 AB F7 07 (random + padding length)
+                               Random (res, res.Length - pad, pad - 1);
+                               res [res.Length - 1] = pad;
+                               Buffer.BlockCopy (inputBuffer, inputOffset, res, full, rem);
+                               // the last padded block will be transformed in-place
+                               InternalTransformBlock (res, full, BlockSizeByte, res, full);
+                               break;
+                       case PaddingMode.PKCS7:
+                               // XX 07 07 07 07 07 07 07 (padding length)
+                               for (int i = res.Length; --i >= (res.Length - pad);) 
+                                       res [i] = pad;
+                               Buffer.BlockCopy (inputBuffer, inputOffset, res, full, rem);
+                               // the last padded block will be transformed in-place
+                               InternalTransformBlock (res, full, BlockSizeByte, res, full);
+                               break;
+                       default:
+                               InternalTransformBlock (inputBuffer, inputOffset, BlockSizeByte, res, outputOffset);
+                               break;
+                       }
+                       return res;
+               }
+
+               private byte[] FinalDecrypt (byte[] inputBuffer, int inputOffset, int inputCount) 
+               {
+                       if ((inputCount % BlockSizeByte) > 0)
+                               throw new CryptographicException ("Invalid input block size.");
+
+                       int total = inputCount;
+                       if (lastBlock)
+                               total += BlockSizeByte;
+
+                       byte[] res = new byte [total];
+                       int outputOffset = 0;
+
+                       if (inputCount > 0)
+                               outputOffset = InternalTransformBlock (inputBuffer, inputOffset, inputCount, res, 0);
+
+                       if (lastBlock) {
+                               Transform (workBuff, 0, res, outputOffset, BlockSizeByte);
+                               outputOffset += BlockSizeByte;
+                               lastBlock = false;
+                       }
+
+                       // total may be 0 (e.g. PaddingMode.None)
+                       byte pad = ((total > 0) ? res [total - 1] : (byte) 0);
+                       switch (padding) {
+                       case PaddingMode.ANSIX923:
+                               if ((pad == 0) || (pad > BlockSizeByte))
+                                       ThrowBadPaddingException (padding, pad, -1);
+                               for (int i = pad - 1; i > 0; i--) {
+                                       if (res [total - 1 - i] != 0x00)
+                                               ThrowBadPaddingException (padding, -1, i);
+                               }
+                               total -= pad;
+                               break;
+                       case PaddingMode.ISO10126:
+                               if ((pad == 0) || (pad > BlockSizeByte))
+                                       ThrowBadPaddingException (padding, pad, -1);
+                               total -= pad;
+                               break;
+                       case PaddingMode.PKCS7:
+                               if ((pad == 0) || (pad > BlockSizeByte))
+                                       ThrowBadPaddingException (padding, pad, -1);
+                               for (int i = pad - 1; i > 0; i--) {
+                                       if (res [total - 1 - i] != pad)
+                                               ThrowBadPaddingException (padding, -1, i);
+                               }
+                               total -= pad;
+                               break;
+                       case PaddingMode.None:  // nothing to do - it's a multiple of block size
+                       case PaddingMode.Zeros: // nothing to do - user must unpad himself
+                               break;
+                       }
+
+                       // return output without padding
+                       if (total > 0) {
+                               byte[] data = new byte [total];
+                               Buffer.BlockCopy (res, 0, data, 0, total);
+                               // zeroize decrypted data (copy with padding)
+                               Array.Clear (res, 0, res.Length);
+                               return data;
+                       }
+                       else
+                               return new byte [0];
+               }
+
+               public virtual byte[] TransformFinalBlock (byte[] inputBuffer, int inputOffset, int inputCount) 
+               {
+                       CheckInput (inputBuffer, inputOffset, inputCount);
+
+                       if (encrypt)
+                               return FinalEncrypt (inputBuffer, inputOffset, inputCount);
+                       else
+                               return FinalDecrypt (inputBuffer, inputOffset, inputCount);
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/CommonCrypto/Makefile b/mcs/class/corlib/CommonCrypto/Makefile
new file mode 100644 (file)
index 0000000..36ea8d3
--- /dev/null
@@ -0,0 +1,8 @@
+thisdir = class/corlib/CommonCrypto
+SUBDIRS =
+include ../../../build/rules.make
+
+.NOTPARALLEL:
+all:
+       MONO_PATH="$(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)$(PLATFORM_PATH_SEPARATOR)$$MONO_PATH" $(RUNTIME) $(RUNTIME_FLAGS) $(topdir)/class/lib/$(BUILD_TOOLS_PROFILE)/commoncryptogenerator.exe
+
diff --git a/mcs/class/corlib/CommonCrypto/RC4CommonCrypto.cs b/mcs/class/corlib/CommonCrypto/RC4CommonCrypto.cs
new file mode 100644 (file)
index 0000000..1e5c4e2
--- /dev/null
@@ -0,0 +1,212 @@
+// A CommonCrypto-based implementation of RC4(tm)
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// (C) 2003 Motus Technologies Inc. (http://www.motus.com)
+// Copyright 2012-2014 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+
+using Crimson.CommonCrypto;
+
+#if MONOTOUCH || XAMMAC
+using Mono.Security.Cryptography;
+
+namespace Mono.Security.Cryptography {
+
+#if !INSIDE_CORLIB
+       public
+#endif
+       sealed partial class ARC4Managed : RC4, ICryptoTransform {
+               
+               IntPtr handle;
+               
+               public ARC4Managed ()
+               {
+               }
+               
+               ~ARC4Managed ()
+               {
+                       Dispose (false);
+               }
+#else
+namespace Crimson.Security.Cryptography {
+
+       public abstract class RC4 : SymmetricAlgorithm {
+
+               private static KeySizes[] s_legalBlockSizes = {
+                       new KeySizes (64, 64, 0)
+               };
+
+               private static KeySizes[] s_legalKeySizes = {
+                       new KeySizes (40, 512, 8)  
+               };
+       
+               public RC4 () 
+               {
+                       KeySizeValue = 128;
+                       BlockSizeValue = 64;
+                       FeedbackSizeValue = BlockSizeValue;
+                       LegalBlockSizesValue = s_legalBlockSizes;
+                       LegalKeySizesValue = s_legalKeySizes;
+               }
+
+               // required for compatibility with .NET 2.0
+               public override byte[] IV {
+                       get { return new byte [0]; }
+                       set { ; }
+               }
+
+               new static public RC4 Create() 
+               {
+                       return Create ("RC4");
+               }
+
+               new static public RC4 Create (string algName) 
+               {
+                       object o = CryptoConfig.CreateFromName (algName);
+                       return (RC4) o ?? new RC4CommonCrypto ();
+               }
+       }
+
+       public sealed class RC4CommonCrypto : RC4, ICryptoTransform {
+               
+               IntPtr handle;
+               
+               public RC4CommonCrypto ()
+               {
+               }
+               
+               ~RC4CommonCrypto ()
+               {
+                       Dispose (false);
+               }
+#endif
+               
+               public bool CanReuseTransform {
+                       get { return false; }
+               }
+
+               public bool CanTransformMultipleBlocks {
+                       get { return true; }
+               }
+               
+               public int InputBlockSize {
+                       get { return 1; }
+               }
+
+               public int OutputBlockSize {
+                       get { return 1; }
+               }
+               
+               public override byte[] Key {
+                       get {
+                               return base.Key;
+                       }
+                       set {
+                               if (value == null)
+                                       throw new ArgumentNullException ("Key");
+
+                               int length = (value.Length << 3);
+                               KeySizeValue = length;
+                               KeyValue = (byte[]) value.Clone ();
+                       }
+               }
+               
+               protected override void Dispose (bool disposing)
+               {
+                       if (handle != IntPtr.Zero) {
+                               Cryptor.CCCryptorRelease (handle);
+                               handle = IntPtr.Zero;
+                       }
+                       base.Dispose (disposing);
+                       GC.SuppressFinalize (this);
+               }
+               
+               public override void GenerateIV ()
+               {
+                       // not used for a stream cipher
+                       IVValue = new byte [0];
+               }
+               
+               public override void GenerateKey ()
+               {
+                       KeyValue = KeyBuilder.Key (KeySizeValue >> 3);
+               }
+               
+               public override ICryptoTransform CreateDecryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       KeyValue = rgbKey;
+                       IVValue = rgbIV;
+                       return this;
+               }
+               
+               public override ICryptoTransform CreateEncryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       KeyValue = rgbKey;
+                       IVValue = rgbIV;
+                       return this;
+               }
+
+               private void CheckInput (byte[] inputBuffer, int inputOffset, int inputCount)
+               {
+                       if (inputBuffer == null)
+                               throw new ArgumentNullException ("inputBuffer");
+                       if (inputOffset < 0)
+                               throw new ArgumentOutOfRangeException ("inputOffset", "< 0");
+                       if (inputCount < 0)
+                               throw new ArgumentOutOfRangeException ("inputCount", "< 0");
+                       // ordered to avoid possible integer overflow
+                       if (inputOffset > inputBuffer.Length - inputCount)
+                               throw new ArgumentException ("inputBuffer", "Overflow");
+               }
+
+               public unsafe int TransformBlock (byte[] inputBuffer, int inputOffset, int inputCount, byte[] outputBuffer, int outputOffset) 
+               {
+                       CheckInput (inputBuffer, inputOffset, inputCount);
+                       if (inputCount == 0)
+                               return 0;
+
+                       // check output parameters
+                       if (outputBuffer == null)
+                               throw new ArgumentNullException ("outputBuffer");
+                       if (outputOffset < 0)
+                               throw new ArgumentOutOfRangeException ("outputOffset", "< 0");
+                       // ordered to avoid possible integer overflow
+                       if (outputOffset > outputBuffer.Length - inputCount)
+                               throw new ArgumentException ("outputBuffer", "Overflow");
+                       if (outputBuffer.Length == 0)
+                               throw new CryptographicException ("output buffer too small");
+                       
+                       if (handle == IntPtr.Zero)
+                               handle = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.RC4, CCOptions.None, KeyValue, IVValue);
+
+                       IntPtr len = IntPtr.Zero;
+                       IntPtr in_len = (IntPtr) (inputBuffer.Length - inputOffset);
+                       IntPtr out_len = (IntPtr) (outputBuffer.Length - outputOffset);
+                       fixed (byte* input = &inputBuffer [0])
+                       fixed (byte* output = &outputBuffer [0]) {
+                               CCCryptorStatus s = Cryptor.CCCryptorUpdate (handle, (IntPtr) (input + inputOffset), in_len, (IntPtr) (output + outputOffset), out_len, ref len);
+                               if ((len != out_len) || (s != CCCryptorStatus.Success))
+                                       throw new CryptographicUnexpectedOperationException (s.ToString ());
+                       }
+                       return (int) out_len;
+               }
+               
+               public byte[] TransformFinalBlock (byte[] inputBuffer, int inputOffset, int inputCount)
+               {
+                       CheckInput (inputBuffer, inputOffset, inputCount);
+                       try {
+                               byte[] output = new byte [inputCount];
+                               TransformBlock (inputBuffer, inputOffset, inputCount, output, 0);
+                               return output;
+                       }
+                       finally {
+                               Cryptor.CCCryptorRelease (handle);
+                               handle = IntPtr.Zero;
+                       }
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/CommonCrypto/RijndaelManaged.cs b/mcs/class/corlib/CommonCrypto/RijndaelManaged.cs
new file mode 100644 (file)
index 0000000..3d528d3
--- /dev/null
@@ -0,0 +1,119 @@
+//
+// RijndaelManaged.cs: Use CommonCrypto AES when possible, 
+//     fallback on RijndaelManagedTransform otherwise
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012 Xamarin Inc.
+//
+
+using System;
+using System.Security.Cryptography;
+
+using Mono.Security.Cryptography;
+using Crimson.CommonCrypto;
+
+namespace System.Security.Cryptography {
+       
+       public sealed class RijndaelManaged : Rijndael {
+               
+               public RijndaelManaged ()
+               {
+               }
+               
+               public override void GenerateIV ()
+               {
+                       IVValue = KeyBuilder.IV (BlockSizeValue >> 3);
+               }
+               
+               public override void GenerateKey ()
+               {
+                       KeyValue = KeyBuilder.Key (KeySizeValue >> 3);
+               }
+               
+               public override ICryptoTransform CreateDecryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       // AES is Rijndael with a 128 bits block size, so we can use CommonCrypto in this case
+                       if (BlockSize == 128) {
+                               IntPtr decryptor = IntPtr.Zero;
+                               switch (Mode) {
+                               case CipherMode.CBC:
+                                       decryptor = Cryptor.Create (CCOperation.Decrypt, CCAlgorithm.AES128, CCOptions.None, rgbKey, rgbIV);
+                                       return new FastCryptorTransform (decryptor, this, false, rgbIV);
+                               case CipherMode.ECB:
+                                       decryptor = Cryptor.Create (CCOperation.Decrypt, CCAlgorithm.AES128, CCOptions.ECBMode, rgbKey, rgbIV);
+                                       return new FastCryptorTransform (decryptor, this, false, rgbIV);
+                               default:
+                                       // CFB cipher mode is not supported by the (old) API we used (for compatibility) so we fallback for them
+                                       // FIXME: benchmark if we're better with RijndaelManagedTransform or CryptorTransform for CFB mode
+                                       break;
+                               }
+                       }
+
+            return NewEncryptor(rgbKey,
+                                ModeValue,
+                                rgbIV,
+                                FeedbackSizeValue,
+                                RijndaelManagedTransformMode.Decrypt);
+               }
+               
+               public override ICryptoTransform CreateEncryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       if (BlockSize == 128) {
+                               IntPtr encryptor = IntPtr.Zero;
+                               switch (Mode) {
+                               case CipherMode.CBC:
+                                       encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.AES128, CCOptions.None, rgbKey, rgbIV);
+                                       return new FastCryptorTransform (encryptor, this, true, rgbIV);
+                               case CipherMode.ECB:
+                                       encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.AES128, CCOptions.ECBMode, rgbKey, rgbIV);
+                                       return new FastCryptorTransform (encryptor, this, true, rgbIV);
+                               default:
+                                       // CFB cipher mode is not supported by the (old) API we used (for compatibility) so we fallback for them
+                                       // FIXME: benchmark if we're better with RijndaelManagedTransform or CryptorTransform for CFB mode
+                                       break;
+                               }
+                       }
+
+            return NewEncryptor(rgbKey,
+                                ModeValue,
+                                rgbIV,
+                                FeedbackSizeValue,
+                                RijndaelManagedTransformMode.Encrypt);
+        }
+
+
+        private ICryptoTransform NewEncryptor (byte[] rgbKey,
+                                               CipherMode mode,
+                                               byte[] rgbIV,
+                                               int feedbackSize,
+                                               RijndaelManagedTransformMode encryptMode) {
+            // Build the key if one does not already exist
+            if (rgbKey == null) {
+                rgbKey = Utils.GenerateRandom(KeySizeValue / 8);
+            }
+
+            // If not ECB mode, make sure we have an IV. In CoreCLR we do not support ECB, so we must have
+            // an IV in all cases.
+#if !FEATURE_CRYPTO
+            if (mode != CipherMode.ECB) {
+#endif // !FEATURE_CRYPTO
+                if (rgbIV == null) {
+                    rgbIV = Utils.GenerateRandom(BlockSizeValue / 8);
+                }
+#if !FEATURE_CRYPTO
+            }
+#endif // !FEATURE_CRYPTO
+
+            // Create the encryptor/decryptor object
+            return new RijndaelManagedTransform (rgbKey,
+                                                 mode,
+                                                 rgbIV,
+                                                 BlockSizeValue,
+                                                 feedbackSize,
+                                                 PaddingValue,
+                                                 encryptMode);
+        }                            
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/CommonCrypto/SecRandom.cs b/mcs/class/corlib/CommonCrypto/SecRandom.cs
new file mode 100644 (file)
index 0000000..a112faf
--- /dev/null
@@ -0,0 +1,81 @@
+//
+// SecRandom.cs: based on Mono's System.Security.Cryptography.RNGCryptoServiceProvider
+//
+// Authors:
+//     Mark Crichton (crichton@gimp.org)
+//     Sebastien Pouliot (sebastien@xamarun.com)
+//
+// (C) 2002
+// Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
+// Copyright (C) 2012-2014 Xamarin Inc.
+//
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+// 
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+// 
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using Crimson.CommonCrypto;
+
+// http://developer.apple.com/library/ios/#DOCUMENTATION/Security/Reference/RandomizationReference/Reference/reference.html
+#if MONOTOUCH || XAMMAC
+namespace System.Security.Cryptography {
+       public class RNGCryptoServiceProvider : RandomNumberGenerator {
+               public RNGCryptoServiceProvider ()
+               {
+               }
+               
+               ~RNGCryptoServiceProvider () 
+               {
+               }
+#else
+using System;
+using System.Security.Cryptography;
+
+namespace Crimson.Security.Cryptography {
+                       
+       public class SecRandom : RandomNumberGenerator {
+#endif
+               
+               public override void GetBytes (byte[] data) 
+               {
+                       if (data == null)
+                               throw new ArgumentNullException ("data");
+                                       
+                       Cryptor.GetRandom (data);
+               }
+               
+               public override void GetNonZeroBytes (byte[] data) 
+               {
+                       if (data == null)
+                               throw new ArgumentNullException ("data");
+
+                       byte[] random = new byte [data.Length * 2];
+                       int i = 0;
+                       // one pass should be enough but hey this is random ;-)
+                       while (i < data.Length) {
+                               Cryptor.GetRandom (random);
+                               for (int j=0; j < random.Length; j++) {
+                                       if (i == data.Length)
+                                               break;
+                                       if (random [j] != 0)
+                                               data [i++] = random [j];
+                               }
+                       }
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/CoreFoundation/CFHelpers.cs b/mcs/class/corlib/CoreFoundation/CFHelpers.cs
new file mode 100644 (file)
index 0000000..7a765d3
--- /dev/null
@@ -0,0 +1,110 @@
+using System;
+using System.Runtime.InteropServices;
+
+namespace XamMac.CoreFoundation
+{
+       internal static class CFHelpers
+       {
+               internal const string CoreFoundationLibrary = "/System/Library/Frameworks/CoreFoundation.framework/CoreFoundation";
+               internal const string SecurityLibrary = "/System/Library/Frameworks/Security.framework/Security";
+
+               [DllImport (CoreFoundationLibrary)]
+               internal extern static void CFRelease (IntPtr obj);
+
+               [DllImport (CoreFoundationLibrary)]
+               internal extern static IntPtr CFRetain (IntPtr obj);
+
+               [StructLayout (LayoutKind.Sequential)]
+               struct CFRange {
+                       public IntPtr loc;
+                       public IntPtr len;
+
+                       public CFRange (int loc, int len)
+                               : this ((long) loc, (long) len)
+                       {
+                       }
+
+                       public CFRange (long l, long len)
+                       {
+                               this.loc = (IntPtr) l;
+                               this.len = (IntPtr) len;
+                       }
+               }
+
+               [DllImport (CoreFoundationLibrary, CharSet=CharSet.Unicode)]
+               extern static IntPtr CFStringCreateWithCharacters (IntPtr allocator, string str, IntPtr count);
+
+               [DllImport (CoreFoundationLibrary, CharSet=CharSet.Unicode)]
+               extern static IntPtr CFStringGetLength (IntPtr handle);
+
+               [DllImport (CoreFoundationLibrary, CharSet=CharSet.Unicode)]
+               extern static IntPtr CFStringGetCharactersPtr (IntPtr handle);
+
+               [DllImport (CoreFoundationLibrary, CharSet=CharSet.Unicode)]
+               extern static IntPtr CFStringGetCharacters (IntPtr handle, CFRange range, IntPtr buffer);
+
+               internal static string FetchString (IntPtr handle)
+               {
+                       if (handle == IntPtr.Zero)
+                               return null;
+
+                       string str;
+
+                       int l = (int)CFStringGetLength (handle);
+                       IntPtr u = CFStringGetCharactersPtr (handle);
+                       IntPtr buffer = IntPtr.Zero;
+                       if (u == IntPtr.Zero){
+                               CFRange r = new CFRange (0, l);
+                               buffer = Marshal.AllocCoTaskMem (l * 2);
+                               CFStringGetCharacters (handle, r, buffer);
+                               u = buffer;
+                       }
+                       unsafe {
+                               str = new string ((char *) u, 0, l);
+                       }
+
+                       if (buffer != IntPtr.Zero)
+                               Marshal.FreeCoTaskMem (buffer);
+
+                       return str;
+               }
+
+               [DllImport (CoreFoundationLibrary)]
+               extern static IntPtr CFDataGetLength (IntPtr handle);
+
+               [DllImport (CoreFoundationLibrary)]
+               extern static IntPtr CFDataGetBytePtr (IntPtr handle);
+
+               internal static byte[] FetchDataBuffer (IntPtr handle)
+               {
+                       var length = (int)CFDataGetLength (handle);
+                       var buffer = new byte [length];
+                       var ptr = CFDataGetBytePtr (handle);
+                       Marshal.Copy (ptr, buffer, 0, buffer.Length);
+                       return buffer;
+               }
+
+               [DllImport (CoreFoundationLibrary)]
+               extern static IntPtr CFDataCreateWithBytesNoCopy (IntPtr allocator, IntPtr bytes, IntPtr length, IntPtr bytesDeallocator);
+
+               [DllImport (CoreFoundationLibrary)]
+               extern static IntPtr CFDataCreate (IntPtr allocator, IntPtr bytes, IntPtr length);
+
+               [DllImport (SecurityLibrary)]
+               extern static IntPtr SecCertificateCreateWithData (IntPtr allocator, IntPtr cfData);
+
+               unsafe internal static IntPtr CreateCertificateFromData (byte[] data)
+               {
+                       fixed (void *ptr = data) {
+                               var cfdata = CFDataCreate (IntPtr.Zero, (IntPtr)ptr, new IntPtr (data.Length));
+                               if (cfdata == IntPtr.Zero)
+                                       return IntPtr.Zero;
+
+                               var certificate = SecCertificateCreateWithData (IntPtr.Zero, cfdata);
+                               if (cfdata != IntPtr.Zero)
+                                       CFRelease (cfdata);
+                               return certificate;
+                       }
+               }
+       }
+}
index 2540e23603143f4999cba59f4c9b11cdc42d6a09..13ad3babf0ce381d79e130b07af2002665ad447b 100644 (file)
@@ -37,6 +37,10 @@ RESOURCE_FILES = \
 
 REFERENCE_SOURCES_FLAGS = -d:FEATURE_PAL,GENERICS_WORK,FEATURE_LIST_PREDICATES,FEATURE_SERIALIZATION,FEATURE_ASCII,FEATURE_LATIN1,FEATURE_UTF7,FEATURE_UTF32,MONO_HYBRID_ENCODING_SUPPORT,FEATURE_ASYNC_IO,NEW_EXPERIMENTAL_ASYNC_IO,FEATURE_UTF32,FEATURE_EXCEPTIONDISPATCHINFO,FEATURE_CORRUPTING_EXCEPTIONS,FEATURE_EXCEPTION_NOTIFICATIONS,FEATURE_STRONGNAME_MIGRATION,FEATURE_USE_LCID,FEATURE_FUSION,FEATURE_CRYPTO,FEATURE_X509_SECURESTRINGS,FEATURE_SYNCHRONIZATIONCONTEXT,FEATURE_SYNCHRONIZATIONCONTEXT_WAIT
 
+ifndef MOBILE_PROFILE
+REFERENCE_SOURCES_FLAGS += -d:FEATURE_MACL
+endif
+
 ifndef MOBILE_STATIC
 REFERENCE_SOURCES_FLAGS += -d:FEATURE_REMOTING,MONO_COM,FEATURE_COMINTEROP,FEATURE_ROLE_BASED_SECURITY
 endif
@@ -60,16 +64,38 @@ WARNING_ABOUT_DISABLED_WARNING=1635
 LOCAL_MCS_FLAGS = -unsafe -nostdlib -nowarn:612,618,$(WARNING_ABOUT_DISABLED_WARNING) -d:INSIDE_CORLIB,MONO_CULTURE_DATA -d:LIBC $(REFERENCE_SOURCES_FLAGS)
 DEFAULT_REFERENCES =
 
-ifdef MOBILE_STATIC
-CORLIB_MONO_POSIX_REF =
-else
-CORLIB_MONO_POSIX_REF = -r:Mono.Posix.dll
+TEST_LIB_REFS = System.Core System
+
+ifndef MOBILE_STATIC
+TEST_LIB_REFS += Mono.Posix
 endif
 
 # System.IO/DirectoryInfoTest.cs needs Mono.Posix
-TEST_MCS_FLAGS += -debug -nowarn:168,219,618,672 -unsafe $(CORLIB_MONO_POSIX_REF) -r:System.Core.dll -r:System.dll \
+TEST_MCS_FLAGS += -debug -nowarn:168,219,618,672 -unsafe \
                                 -define:MONO_DATACONVERTER_STATIC_METHODS $(TEST_RESX_RESOURCES:%=-resource:%)
 
+
+CC_PROFILE := $(filter monotouch% xammac, $(PROFILE))
+ifdef CC_PROFILE
+
+BUILT_SOURCES = \
+       CommonCrypto/MD5CryptoServiceProvider.g.cs      \
+       CommonCrypto/SHA256Managed.g.cs \
+       CommonCrypto/RC2CryptoServiceProvider.g.cs \
+       CommonCrypto/SHA384Managed.g.cs \
+       CommonCrypto/DESCryptoServiceProvider.g.cs \
+       CommonCrypto/SHA1CryptoServiceProvider.g.cs     \
+       CommonCrypto/SHA512Managed.g.cs \
+       CommonCrypto/MD2Managed.g.cs \
+       CommonCrypto/SHA1Managed.g.cs \
+       CommonCrypto/TripleDESCryptoServiceProvider.g.cs \
+       CommonCrypto/MD4Managed.g.cs
+
+CommonCrypto/%.g.cs:
+       $(MAKE) -C CommonCrypto
+
+endif
+
 EXTRA_DISTFILES = \
        Test/resources/MyResources.resources    \
        Test/resources/MyResources.de.resources \
@@ -107,11 +133,11 @@ $(test_lib): $(TEST_RESOURCES) $(satellite_assembly1) $(satellite_assembly2)
 
 $(satellite_assembly1): Test/resources/culture-es-ES.cs Test/resources/Resources.es-ES.resources
        @mkdir -p es-ES
-       $(CSCOMPILE) -target:library -r:$(corlib) Test/resources/culture-es-ES.cs -resource:Test/resources/Resources.es-ES.resources -out:$@
+       $(CSCOMPILE) -target:library -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll Test/resources/culture-es-ES.cs -resource:Test/resources/Resources.es-ES.resources -out:$@
 
 $(satellite_assembly2): Test/resources/culture-nn-NO.cs Test/resources/Resources.nn-NO.resources
        @mkdir -p nn-NO
-       $(CSCOMPILE) -target:library -r:$(corlib) Test/resources/culture-nn-NO.cs -resource:Test/resources/Resources.nn-NO.resources -out:$@
+       $(CSCOMPILE) -target:library -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll Test/resources/culture-nn-NO.cs -resource:Test/resources/Resources.nn-NO.resources -out:$@
 
 vtsdir = Test/System.Runtime.Serialization.Formatters.Binary/VersionTolerantSerialization
 vtslibs = \
@@ -126,11 +152,13 @@ test-vts: $(vtslibs) $(vtsdir)/$(PROFILE)_TestLib/BinarySerializationOverVersion
 
 $(vtsdir)/$(PROFILE)_TestLib/%/Address.dll: $(vtsdir)/VersionTolerantSerializationTestLib/%/Address.cs
        @mkdir -p $(dir $@)
-       $(CSCOMPILE) -target:library -r:$(corlib) -warn:0 -out:$@ $^
+       $(CSCOMPILE) -target:library -warn:0 -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll -out:$@ $^
 
 $(vtsdir)/$(PROFILE)_TestLib/BinarySerializationOverVersions.exe: $(vtsdir)/BinarySerializationOverVersions.cs $(vtsdir)/$(PROFILE)_TestLib/1.0/Address.dll $(test_nunit_dep)
-       $(CSCOMPILE) $(test_nunit_ref) -warn:0 -r:$(corlib) \
+       $(CSCOMPILE) $(test_nunit_ref) -warn:0 \
                -r:$(vtsdir)/$(PROFILE)_TestLib/1.0/Address.dll \
+               -r:$(topdir)/class/lib/$(PROFILE)/mscorlib.dll \
+               -r:$(topdir)/class/lib/$(PROFILE)/System.dll \
                $(vtsdir)/BinarySerializationOverVersions.cs -out:$@
        @cp $(vtsdir)/$(PROFILE)_TestLib/1.0/Address.dll $(vtsdir)/$(PROFILE)_TestLib
 
index b97f416a83d50549462a94c2bb9b9f9fd10a9c78..88d713ed8c2a87836d455ed7d2884e0e47c8bd06 100644 (file)
@@ -68,7 +68,7 @@ namespace Mono.Interop
                {
                        // called from unmanaged code after .ctor is invoked
                        // we need .ctor to create unmanaged object and thus IUnknown property value
-                       if (FindProxy(com_object.IUnknown) == null)
+                       if (FindProxy (com_object.IUnknown) == null)
                                AddProxy (com_object.IUnknown, this);
                        else
                                System.Threading.Interlocked.Increment (ref ref_count);
@@ -82,7 +82,7 @@ namespace Mono.Interop
                internal ComInteropProxy (IntPtr pUnk, Type t)
                        : base (t)
                {
-                       com_object = new __ComObject (pUnk);
+                       com_object = new __ComObject (pUnk, this);
                        CacheProxy ();
                }
 
@@ -108,17 +108,20 @@ namespace Mono.Interop
                // already known, a cached proxy will be returned.
                internal static ComInteropProxy CreateProxy (Type t)
                {
-                       ComInteropProxy proxy = new ComInteropProxy (t);
-                       proxy.com_object.Initialize (t);
-
-                       ComInteropProxy cachedProxy = FindProxy (proxy.com_object.IUnknown);
+                       IntPtr iunknown = __ComObject.CreateIUnknown (t);
+                       ComInteropProxy proxy;
+                       ComInteropProxy cachedProxy = FindProxy (iunknown);
                        if (cachedProxy != null) {
                                // check that the COM type of the cached proxy matches
                                // the requested type. See 2nd part of bug #520437.
                                Type cachedType = cachedProxy.com_object.GetType ();
                                if (cachedType != t)
                                        throw new InvalidCastException (String.Format ("Unable to cast object of type '{0}' to type '{1}'.", cachedType, t));
-                               return cachedProxy;
+                               proxy = cachedProxy;
+                               Marshal.Release (iunknown);
+                       } else {
+                               proxy = new ComInteropProxy (t);
+                               proxy.com_object.Initialize (iunknown, proxy);
                        }
                        return proxy;
                }
index ce498cb17c52dda886e1cee61a393f79114239b1..bedcf1af0c14a5bb94af6c4dc4bfc29dc8fc19a8 100644 (file)
@@ -602,6 +602,12 @@ namespace System
                        get;
                }
 
+#if MOBILE
+               static int get_core_clr_security_level ()
+               {
+                       return 1;
+               }
+#else
                //seclevel { transparent = 0, safe-critical = 1, critical = 2}
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
                public extern int get_core_clr_security_level ();
@@ -616,6 +622,7 @@ namespace System
 
                public override bool IsSecuritySafeCritical {
                        get { return get_core_clr_security_level () == 1; }
-               }               
+               }
+#endif
        }
 }
index a732d3eba0f5a602e660905a6b47db23f99ff5a8..aefc8b908f3bd79b5590e4beb52e2bb5356806ed 100644 (file)
@@ -1,16 +1,72 @@
+using System.IO;
+
 namespace Microsoft.Win32
 {
        static class Win32Native
        {
                internal const string ADVAPI32 = "advapi32.dll";
 
+               // Error codes from WinError.h
                internal const int ERROR_SUCCESS = 0x0;
+               internal const int ERROR_INVALID_FUNCTION = 0x1;
+               internal const int ERROR_FILE_NOT_FOUND = 0x2;
+               internal const int ERROR_PATH_NOT_FOUND = 0x3;
+               internal const int ERROR_ACCESS_DENIED  = 0x5;
+               internal const int ERROR_INVALID_HANDLE = 0x6;
+               internal const int ERROR_NOT_ENOUGH_MEMORY = 0x8;
+               internal const int ERROR_INVALID_DATA = 0xd;
+               internal const int ERROR_INVALID_DRIVE = 0xf;
+               internal const int ERROR_NO_MORE_FILES = 0x12;
+               internal const int ERROR_NOT_READY = 0x15;
+               internal const int ERROR_BAD_LENGTH = 0x18;
+               internal const int ERROR_SHARING_VIOLATION = 0x20;
+               internal const int ERROR_NOT_SUPPORTED = 0x32;
+               internal const int ERROR_FILE_EXISTS = 0x50;
+               internal const int ERROR_INVALID_PARAMETER = 0x57;
+               internal const int ERROR_BROKEN_PIPE = 0x6D;
+               internal const int ERROR_CALL_NOT_IMPLEMENTED = 0x78;
+               internal const int ERROR_INSUFFICIENT_BUFFER = 0x7A;
+               internal const int ERROR_INVALID_NAME = 0x7B;
+               internal const int ERROR_BAD_PATHNAME = 0xA1;
+               internal const int ERROR_ALREADY_EXISTS = 0xB7;
+               internal const int ERROR_ENVVAR_NOT_FOUND = 0xCB;
+               internal const int ERROR_FILENAME_EXCED_RANGE = 0xCE;  // filename too long.
+               internal const int ERROR_NO_DATA = 0xE8;
+               internal const int ERROR_PIPE_NOT_CONNECTED = 0xE9;
+               internal const int ERROR_MORE_DATA = 0xEA;
+               internal const int ERROR_DIRECTORY = 0x10B;
+               internal const int ERROR_OPERATION_ABORTED = 0x3E3;  // 995; For IO Cancellation
+               internal const int ERROR_NOT_FOUND = 0x490;          // 1168; For IO Cancellation
+               internal const int ERROR_NO_TOKEN = 0x3f0;
+               internal const int ERROR_DLL_INIT_FAILED = 0x45A;
+               internal const int ERROR_NON_ACCOUNT_SID = 0x4E9;
+               internal const int ERROR_NOT_ALL_ASSIGNED = 0x514;
+               internal const int ERROR_UNKNOWN_REVISION = 0x519;
+               internal const int ERROR_INVALID_OWNER = 0x51B;
+               internal const int ERROR_INVALID_PRIMARY_GROUP = 0x51C;
+               internal const int ERROR_NO_SUCH_PRIVILEGE = 0x521;
+               internal const int ERROR_PRIVILEGE_NOT_HELD = 0x522;
+               internal const int ERROR_NONE_MAPPED = 0x534;
+               internal const int ERROR_INVALID_ACL = 0x538;
+               internal const int ERROR_INVALID_SID = 0x539;
+               internal const int ERROR_INVALID_SECURITY_DESCR = 0x53A;
+               internal const int ERROR_BAD_IMPERSONATION_LEVEL = 0x542;
+               internal const int ERROR_CANT_OPEN_ANONYMOUS = 0x543;
+               internal const int ERROR_NO_SECURITY_ON_OBJECT = 0x546;
+               internal const int ERROR_TRUSTED_RELATIONSHIP_FAILURE = 0x6FD;
+
+               internal const FileAttributes FILE_ATTRIBUTE_DIRECTORY = FileAttributes.Directory;
 
                public static string GetMessage (int hr)
                {
                        return "Error " + hr;
                }
 
+               public static int MakeHRFromErrorCode (int errorCode)
+               {
+                       return unchecked(((int)0x80070000) | errorCode);
+               }
+
                public class SECURITY_ATTRIBUTES
                {
 
index 2593f96c68d372382cf6f37764c29f9966fe58bf..702cd540d976d92e34dbce66fc2e116a679f2603 100644 (file)
@@ -60,9 +60,6 @@ namespace System.Diagnostics {
                #pragma warning restore 649
                #endregion
 
-               [MethodImplAttribute (MethodImplOptions.InternalCall)]
-               extern static int GetILOffsetFromFile (string path, int methodToken, uint methodIndex, int nativeOffset);
-
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
                extern static bool get_frame_info (int skip, bool needFileInfo, out MethodBase method,
                                                   out int iloffset, out int native_offset,
index 4c322cd107fc95a732c4763db1ffb5bd675d57c9..65ca59de4f3f17defb8a2b789c20637b33d2d02b 100644 (file)
@@ -219,17 +219,14 @@ namespace System.Diagnostics {
                        return i != 0;
                }
 
-               // This method is also used with reflection by mono-symbolicate tool.
-               // mono-symbolicate tool uses this method to check which method matches
-               // the stack frame method signature.
-               static void GetFullNameForStackTrace (StringBuilder sb, MethodBase mi)
+               public static void GetFullNameForStackTrace (StringBuilder sb, MethodBase mi)
                {
                        var declaringType = mi.DeclaringType;
                        if (declaringType.IsGenericType && !declaringType.IsGenericTypeDefinition)
                                declaringType = declaringType.GetGenericTypeDefinition ();
 
                        // Get generic definition
-                       var bindingflags = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic;
+                       const BindingFlags bindingflags = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic;
                        foreach (var m in declaringType.GetMethods (bindingflags)) {
                                if (m.MetadataToken == mi.MetadataToken) {
                                        mi = m;
@@ -253,7 +250,7 @@ namespace System.Diagnostics {
                                sb.Append ("]");
                        }
 
-                       ParameterInfo[] p = mi.GetParametersInternal ();
+                       ParameterInfo[] p = mi.GetParameters ();
 
                        sb.Append (" (");
                        for (int i = 0; i < p.Length; ++i) {
@@ -264,18 +261,15 @@ namespace System.Diagnostics {
                                if (pt.IsGenericType && ! pt.IsGenericTypeDefinition)
                                        pt = pt.GetGenericTypeDefinition ();
 
-                               if (pt.IsClass && !String.IsNullOrEmpty (pt.Namespace)) {
-                                       sb.Append (pt.Namespace);
-                                       sb.Append (".");
-                               }
-                               sb.Append (pt.Name);
+                               sb.Append (pt.ToString());
+
                                if (p [i].Name != null) {
                                        sb.Append (" ");
                                        sb.Append (p [i].Name);
                                }
                        }
                        sb.Append (")");
-               }
+               }               
 
                public override string ToString ()
                {
index 297a4d376c308a80d56b20fea5c0e83c47da3821..b755b4d5091913e9896dffce497d314bb1419236 100644 (file)
@@ -59,7 +59,6 @@ namespace System.Globalization
                [NonSerialized]
                int default_calendar_type;
                bool m_useUserOverride;
-               [NonSerialized]
                internal volatile NumberFormatInfo numInfo;
                internal volatile DateTimeFormatInfo dateTimeInfo;
                volatile TextInfo textInfo;
index f263eeb1cc9c5673811165cf436fbfb7693285ff..ed773f6ca6a4505c369c790a608b55bcfb0617af 100644 (file)
@@ -96,7 +96,7 @@ namespace System.IO
                                 info.Parent.Create ();
 
                        MonoIOError error;
-                       if (!MonoIO.CreateDirectory (path, out error)) {
+                       if (!MonoIO.CreateDirectory (info.FullName, out error)) {
                                // LAMESPEC: 1.1 and 1.2alpha allow CreateDirectory on a file path.
                                // So CreateDirectory ("/tmp/somefile") will succeed if 'somefile' is
                                // not a directory. However, 1.0 will throw an exception.
@@ -645,5 +645,28 @@ namespace System.IO
                                                 AccessControlSections.Group |
                                                 AccessControlSections.Access);
                }
+
+#region Copied from reference source
+        internal static String GetDemandDir(string fullPath, bool thisDirOnly)
+        {
+            String demandPath;
+
+            if (thisDirOnly) {
+                if (fullPath.EndsWith( Path.DirectorySeparatorChar ) 
+                    || fullPath.EndsWith( Path.AltDirectorySeparatorChar ) )
+                    demandPath = fullPath + ".";
+                else
+                    demandPath = fullPath + Path.DirectorySeparatorCharAsString + ".";
+            }
+            else {
+                if (!(fullPath.EndsWith( Path.DirectorySeparatorChar ) 
+                    || fullPath.EndsWith( Path.AltDirectorySeparatorChar )) )
+                    demandPath = fullPath + Path.DirectorySeparatorCharAsString;
+                else
+                    demandPath = fullPath;
+            }
+            return demandPath;
+        }
+#endregion
        }
 }
index 8289c288c20ffe228d3133c28a4c4569bf05b9d1..d25432dcacdf559da372f14a60dde2ff5ca36fbb 100644 (file)
@@ -62,7 +62,7 @@ namespace System.IO {
 
                        FullPath = Path.GetFullPath (path);
                        if (simpleOriginalPath)
-                               OriginalPath = Path.GetFileName (path);
+                               OriginalPath = Path.GetFileName (FullPath);
                        else
                                OriginalPath = path;
 
@@ -102,12 +102,13 @@ namespace System.IO {
 
                public override bool Exists {
                        get {
-                               Refresh (false);
+                               if (_dataInitialised == -1)
+                                       Refresh ();
 
-                               if (stat.Attributes == MonoIO.InvalidFileAttributes)
+                               if (_data.fileAttributes == MonoIO.InvalidFileAttributes)
                                        return false;
 
-                               if ((stat.Attributes & FileAttributes.Directory) == 0)
+                               if ((_data.fileAttributes & FileAttributes.Directory) == 0)
                                        return false;
 
                                return true;
@@ -458,6 +459,19 @@ namespace System.IO {
                        }
                }
                
-               
+               internal void CheckPath (string path)
+               {
+                       if (path == null)
+                               throw new ArgumentNullException ("path");
+                       if (path.Length == 0)
+                               throw new ArgumentException ("An empty file name is not valid.");
+                       if (path.IndexOfAny (Path.InvalidPathChars) != -1)
+                               throw new ArgumentException ("Illegal characters in path.");
+                       if (Environment.IsRunningOnWindows) {
+                               int idx = path.IndexOf (':');
+                               if (idx >= 0 && idx != 1)
+                                       throw new ArgumentException ("path");
+                       }
+               }
        }
 }
index 8f4b57290c822e271064aadd68ae09223bed966d..c6c32095cbf9aa19e422c014d1bcf41e32e43901 100644 (file)
@@ -113,6 +113,21 @@ namespace System.IO
                        }
                }
 
+               internal static String InternalCopy (String sourceFileName, String destFileName, bool overwrite, bool checkHost)
+               {
+                       String fullSourceFileName = Path.GetFullPathInternal(sourceFileName);
+                       String fullDestFileName = Path.GetFullPathInternal(destFileName);
+
+                       MonoIOError error;
+
+                       if (!MonoIO.CopyFile (fullSourceFileName, fullDestFileName, overwrite, out error)) {
+                               string p = Locale.GetText ("{0}\" or \"{1}", sourceFileName, destFileName);
+                               throw MonoIO.GetException (p, error);
+                       }
+
+                       return fullDestFileName;
+               }
+
                public static FileStream Create (string path)
                {
                        return Create (path, 8192);
@@ -406,6 +421,12 @@ namespace System.IO
                                                               "Destination and backup arguments are the same file."));
                        }
 
+                       var attrs = GetAttributes (fullDest);
+
+                       // TODO: Should be done in wapi, win32 api handles this already
+                       if ((attrs & FileAttributes.ReadOnly) != 0)
+                               throw MonoIO.GetException (MonoIOError.ERROR_ACCESS_DENIED);
+
                        if (!MonoIO.ReplaceFile (fullSource, fullDest, fullBackup, 
                                                 ignoreMetadataErrors, out error)) {
                                throw MonoIO.GetException (error);
@@ -688,5 +709,22 @@ namespace System.IO
                                        w.WriteLine (line);
                        }
                }
+
+               internal static int FillAttributeInfo (String path, ref MonoIOStat data, bool tryagain, bool returnErrorOnNotFound)
+               {
+                       if (tryagain)
+                               throw new NotImplementedException ();
+
+                       MonoIOError error;
+                       MonoIO.GetFileStat (path, out data, out error);
+
+                       if (!returnErrorOnNotFound && (error == MonoIOError.ERROR_FILE_NOT_FOUND || error == MonoIOError.ERROR_PATH_NOT_FOUND || error == MonoIOError.ERROR_NOT_READY)) {
+                               data = default (MonoIOStat);
+                               data.fileAttributes = (FileAttributes) (-1);
+                               return 0;
+                       }
+
+                       return (int) error;
+               }
        }
 }
diff --git a/mcs/class/corlib/System.IO/FileInfo.cs b/mcs/class/corlib/System.IO/FileInfo.cs
deleted file mode 100644 (file)
index 1e53bad..0000000
+++ /dev/null
@@ -1,331 +0,0 @@
-//------------------------------------------------------------------------------
-// 
-// System.IO.FileInfo.cs 
-//
-// Copyright (C) 2001 Moonlight Enterprises, All Rights Reserved
-// 
-// Author:         Jim Richardson, develop@wtfo-guru.com
-//                 Dan Lewis (dihlewis@yahoo.co.uk)
-// Created:        Monday, August 13, 2001 
-//
-//------------------------------------------------------------------------------
-
-//
-// Copyright (C) 2004, 2006 Novell, Inc (http://www.novell.com)
-//
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System.Runtime.InteropServices;
-using System.Runtime.Serialization;
-using System.Security;
-
-#if !MOBILE
-using System.Security.AccessControl;
-#endif
-
-namespace System.IO {
-
-       [Serializable]
-       [ComVisible (true)]
-       public sealed class FileInfo : FileSystemInfo
-       {
-               private bool exists;
-
-               public FileInfo (string fileName)
-               {
-                       if (fileName == null)
-                               throw new ArgumentNullException ("fileName");
-
-                       CheckPath (fileName);
-                       SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
-
-                       OriginalPath = fileName;
-                       FullPath = Path.GetFullPath (fileName);
-               }
-
-               private FileInfo (SerializationInfo info, StreamingContext context)
-                       : base (info, context)
-               {
-               }
-
-               internal override void InternalRefresh ()
-               {
-                       exists = File.Exists (FullPath);
-               }
-
-               // public properties
-
-               public override bool Exists {
-                       get {
-                               Refresh (false);
-
-                               if (stat.Attributes == MonoIO.InvalidFileAttributes)
-                                       return false;
-
-                               if ((stat.Attributes & FileAttributes.Directory) != 0)
-                                       return false;
-
-                               return exists;
-                       }
-               }
-
-               public override string Name {
-                       get {
-                               return Path.GetFileName (FullPath);
-                       }
-               }
-
-               public bool IsReadOnly {
-                       get {
-                               if (!Exists)
-                                       throw new FileNotFoundException ("Could not find file \"" + OriginalPath + "\".", OriginalPath);
-                                       
-                               return ((stat.Attributes & FileAttributes.ReadOnly) != 0);
-                       }
-                               
-                       set {
-                               if (!Exists)
-                                       throw new FileNotFoundException ("Could not find file \"" + OriginalPath + "\".", OriginalPath);
-                                       
-                               FileAttributes attrs = File.GetAttributes(FullPath);
-
-                               if (value) 
-                                       attrs |= FileAttributes.ReadOnly;
-                               else
-                                       attrs &= ~FileAttributes.ReadOnly;
-
-                               File.SetAttributes(FullPath, attrs);
-                       }
-               }
-
-               [MonoLimitation ("File encryption isn't supported (even on NTFS).")]
-               [ComVisible (false)]
-               public void Encrypt ()
-               {
-                       // MS.NET support this only on NTFS file systems, i.e. it's a file-system (not a framework) feature.
-                       // otherwise it throws a NotSupportedException (or a PlatformNotSupportedException on older OS).
-                       // we throw the same (instead of a NotImplementedException) because most code should already be
-                       // handling this exception to work properly.
-                       throw new NotSupportedException (Locale.GetText ("File encryption isn't supported on any file system."));
-               }
-
-               [MonoLimitation ("File encryption isn't supported (even on NTFS).")]
-               [ComVisible (false)]
-               public void Decrypt ()
-               {
-                       // MS.NET support this only on NTFS file systems, i.e. it's a file-system (not a framework) feature.
-                       // otherwise it throws a NotSupportedException (or a PlatformNotSupportedException on older OS).
-                       // we throw the same (instead of a NotImplementedException) because most code should already be
-                       // handling this exception to work properly.
-                       throw new NotSupportedException (Locale.GetText ("File encryption isn't supported on any file system."));
-               }
-
-               public long Length {
-                       get {
-                               if (!Exists)
-                                       throw new FileNotFoundException ("Could not find file \"" + OriginalPath + "\".", OriginalPath);
-
-                               return stat.Length;
-                       }
-               }
-
-               public string DirectoryName {
-                       get {
-                               return Path.GetDirectoryName (FullPath);
-                       }
-               }
-
-               public DirectoryInfo Directory {
-                       get {
-                               return new DirectoryInfo (DirectoryName);
-                       }
-               }
-
-               // streamreader methods
-
-               public StreamReader OpenText ()
-               {
-                       return new StreamReader (Open (FileMode.Open, FileAccess.Read));
-               }
-
-               public StreamWriter CreateText ()
-               {
-                       return new StreamWriter (Open (FileMode.Create, FileAccess.Write));
-               }
-               
-               public StreamWriter AppendText ()
-               {
-                       return new StreamWriter (Open (FileMode.Append, FileAccess.Write));
-               }
-
-               // filestream methods
-
-               public FileStream Create ()
-               {
-                       return File.Create (FullPath);
-               }
-
-               public FileStream OpenRead ()
-               {
-                       return Open (FileMode.Open, FileAccess.Read, FileShare.Read);
-               }
-
-               public FileStream OpenWrite ()
-               {
-                       return Open (FileMode.OpenOrCreate, FileAccess.Write);
-               }
-
-               public FileStream Open (FileMode mode)
-               {
-                       return Open (mode, FileAccess.ReadWrite);
-               }
-
-               public FileStream Open (FileMode mode, FileAccess access)
-               {
-                       return Open (mode, access, FileShare.None);
-               }
-
-               public FileStream Open (FileMode mode, FileAccess access, FileShare share)
-               {
-                       return new FileStream (FullPath, mode, access, share);
-               }
-
-               // file methods
-
-               public override void Delete ()
-               {
-                       MonoIOError error;
-
-                       SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
-
-                       if (!MonoIO.Exists (FullPath, out error))
-                               // a weird MS.NET behaviour
-                               return;
-
-                       if (MonoIO.ExistsDirectory (FullPath, out error))
-                               throw new UnauthorizedAccessException ("Access to the path \"" + FullPath + "\" is denied.");
-                       if (!MonoIO.DeleteFile (FullPath, out error))
-                               throw MonoIO.GetException (OriginalPath, error);
-               }
-
-               public void MoveTo (string destFileName)
-               {
-                       if (destFileName == null)
-                               throw new ArgumentNullException ("destFileName");
-                       if (destFileName.Length == 0)
-                               throw new ArgumentException ("An empty file name is not valid.", "destFileName");
-
-                       var destFullPath = Path.GetFullPath (destFileName);
-                       if (destFullPath == FullPath)
-                               return;
-                       if (!File.Exists (FullPath))
-                               throw new FileNotFoundException ();
-
-                       File.Move (FullPath, destFullPath);
-                       this.FullPath = destFullPath;
-               }
-
-               public FileInfo CopyTo (string destFileName)
-               {
-                       return CopyTo (destFileName, false);
-               }
-
-               public FileInfo CopyTo (string destFileName, bool overwrite)
-               {
-                       if (destFileName == null)
-                               throw new ArgumentNullException ("destFileName");
-                       if (destFileName.Length == 0)
-                               throw new ArgumentException ("An empty file name is not valid.", "destFileName");
-
-                       string dest = Path.GetFullPath (destFileName);
-
-                       if (overwrite && File.Exists (dest))
-                               File.Delete (dest);
-
-                       File.Copy (FullPath, dest);
-               
-                       return new FileInfo (dest);
-               }
-
-               public override string ToString ()
-               {
-                       return OriginalPath;
-               }
-
-#if !MOBILE
-               public FileSecurity GetAccessControl ()
-               {
-                       return File.GetAccessControl (FullPath); 
-               }
-               
-               public FileSecurity GetAccessControl (AccessControlSections includeSections)
-               {
-                       return File.GetAccessControl (FullPath, includeSections);
-               }
-
-               [ComVisible (false)]
-               public FileInfo Replace (string destinationFileName,
-                                        string destinationBackupFileName)
-               {
-                       string destinationFullPath = null;
-                       if (!Exists)
-                               throw new FileNotFoundException ();
-                       if (destinationFileName == null)
-                               throw new ArgumentNullException ("destinationFileName");
-                       if (destinationFileName.Length == 0)
-                               throw new ArgumentException ("An empty file name is not valid.", "destinationFileName");
-
-                       destinationFullPath = Path.GetFullPath (destinationFileName);
-
-                       if (!File.Exists (destinationFullPath))
-                               throw new FileNotFoundException ();
-
-                       FileAttributes attrs = File.GetAttributes (destinationFullPath);
-
-                       if ( (attrs & FileAttributes.ReadOnly) == FileAttributes.ReadOnly)
-                                       throw new UnauthorizedAccessException (); 
-
-                       if (destinationBackupFileName != null) {
-                               if (destinationBackupFileName.Length == 0)
-                                       throw new ArgumentException ("An empty file name is not valid.", "destinationBackupFileName");
-                               File.Copy (destinationFullPath, Path.GetFullPath (destinationBackupFileName), true);
-                       }
-                       File.Copy (FullPath, destinationFullPath,true);
-                       File.Delete (FullPath);
-                       return new FileInfo (destinationFullPath);
-               }
-               
-               [ComVisible (false)]
-               [MonoLimitation ("We ignore the ignoreMetadataErrors parameter")]
-               public FileInfo Replace (string destinationFileName,
-                                        string destinationBackupFileName,
-                                        bool ignoreMetadataErrors)
-               {
-                       return Replace (destinationFileName, destinationBackupFileName);
-               }
-
-               public void SetAccessControl (FileSecurity fileSecurity)
-               {
-                       File.SetAccessControl (FullPath, fileSecurity);
-               }
-#endif
-       }
-}
diff --git a/mcs/class/corlib/System.IO/FileSystemInfo.cs b/mcs/class/corlib/System.IO/FileSystemInfo.cs
deleted file mode 100644 (file)
index 9c2c3fa..0000000
+++ /dev/null
@@ -1,270 +0,0 @@
-//------------------------------------------------------------------------------
-// 
-// System.IO.FileSystemInfo.cs 
-//
-// Copyright (C) 2001 Moonlight Enterprises, All Rights Reserved
-// Copyright 2011 Xamarin Inc (http://www.xamarin.com).
-// 
-// Author:         Jim Richardson, develop@wtfo-guru.com
-//                 Dan Lewis (dihlewis@yahoo.co.uk)
-// Created:        Monday, August 13, 2001 
-//
-//------------------------------------------------------------------------------
-
-//
-// Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
-//
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System.Runtime.InteropServices;
-using System.Runtime.Serialization;
-using System.Security;
-using System.Security.Permissions;
-
-namespace System.IO {
-       
-       [Serializable]
-       [FileIOPermission (SecurityAction.InheritanceDemand, Unrestricted = true)]
-       [ComVisible (true)]
-#if NET_2_1
-       public abstract class FileSystemInfo {
-#else
-       public abstract class FileSystemInfo : MarshalByRefObject, ISerializable {
-
-               #region Implementation of ISerializable
-
-               [ComVisible(false)]
-               public virtual void GetObjectData (SerializationInfo info, StreamingContext context)
-               {
-                       info.AddValue ("OriginalPath", OriginalPath, typeof(string));
-                       info.AddValue ("FullPath", FullPath, typeof(string));
-               }
-
-               #endregion Implementation of ISerializable
-#endif
-               // public properties
-
-               public abstract bool Exists { get; }
-
-               public abstract string Name { get; }
-
-               public virtual string FullName {
-                       get {
-                               return FullPath;
-                       }
-               }
-
-               public string Extension {
-                       get {
-                               return Path.GetExtension (Name);
-                       }
-               }
-
-               public FileAttributes Attributes {
-                       get {
-                               Refresh (false);
-                               return stat.Attributes;
-                       }
-
-                       set {
-                               MonoIOError error;
-                               
-                               if (!MonoIO.SetFileAttributes (FullName,
-                                                              value,
-                                                              out error))
-                                       throw MonoIO.GetException (FullName,
-                                                                  error);
-                               Refresh (true);
-                       }
-               }
-
-               public DateTime CreationTime {
-                       get {
-                               Refresh (false);
-                               return DateTime.FromFileTime (stat.CreationTime);
-                       }
-
-                       set {
-                               SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
-
-                               long filetime = value.ToFileTime ();
-                       
-                               MonoIOError error;
-                               
-                               if (!MonoIO.SetFileTime (FullName, filetime,
-                                                        -1, -1, out error))
-                                       throw MonoIO.GetException (FullName,
-                                                                  error);
-                               Refresh (true);
-                       }
-               }
-
-               [ComVisible(false)]
-               public DateTime CreationTimeUtc {
-                       get {
-                               return CreationTime.ToUniversalTime ();
-                       }
-
-                       set {
-                               CreationTime = value.ToLocalTime ();
-                       }
-               }
-
-               public DateTime LastAccessTime {
-                       get {
-                               Refresh (false);
-                               return DateTime.FromFileTime (stat.LastAccessTime);
-                       }
-
-                       set {
-                               SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
-
-                               long filetime = value.ToFileTime ();
-
-                               MonoIOError error;
-                               
-                               if (!MonoIO.SetFileTime (FullName, -1,
-                                                        filetime, -1,
-                                                        out error))
-                                       throw MonoIO.GetException (FullName,
-                                                                  error);
-                               Refresh (true);
-                       }
-               }
-
-               [ComVisible(false)]
-               public DateTime LastAccessTimeUtc {
-                       get {
-                               Refresh (false);
-                               return LastAccessTime.ToUniversalTime ();
-                       }
-
-                       set {
-                               LastAccessTime = value.ToLocalTime ();
-                       }
-               }
-
-               public DateTime LastWriteTime {
-                       get {
-                               Refresh (false);
-                               return DateTime.FromFileTime (stat.LastWriteTime);
-                       }
-
-                       set {
-                               SecurityManager.EnsureElevatedPermissions (); // this is a no-op outside moonlight
-
-                               long filetime = value.ToFileTime ();
-
-                               MonoIOError error;
-                               
-                               if (!MonoIO.SetFileTime (FullName, -1, -1,
-                                                        filetime, out error))
-                                       throw MonoIO.GetException (FullName,
-                                                                  error);
-                               Refresh (true);
-                       }
-               }
-
-               [ComVisible(false)]
-               public DateTime LastWriteTimeUtc {
-                       get {
-                               Refresh (false);
-                               return LastWriteTime.ToUniversalTime ();
-                       }
-
-                       set {
-                               LastWriteTime = value.ToLocalTime ();
-                       }
-               }
-
-               // public methods
-
-               public abstract void Delete ();
-
-               public void Refresh ()
-               {
-                       Refresh (true);
-               }
-
-               // protected
-
-               protected FileSystemInfo ()
-               {
-                       this.valid = false;
-                       this.FullPath = null;
-               }
-
-               protected FileSystemInfo (SerializationInfo info, StreamingContext context)
-               {
-                       if (info == null)
-                       {
-                               throw new ArgumentNullException("info");
-                       }
-
-                       FullPath = info.GetString("FullPath");
-                       OriginalPath = info.GetString("OriginalPath");
-               }
-
-               protected string FullPath;
-               protected string OriginalPath;
-
-               // internal
-
-               internal void Refresh (bool force)
-               {
-                       if (valid && !force)
-                               return;
-
-                       MonoIOError error;
-                       
-                       MonoIO.GetFileStat (FullName, out stat, out error);
-                       /* Don't throw on error here, too much other
-                        * stuff relies on it not doing so...
-                        */
-                       
-                       valid = true;
-                       
-                       InternalRefresh ();
-               }
-               
-               internal virtual void InternalRefresh ()
-               {
-               }
-
-               internal void CheckPath (string path)
-               {
-                       if (path == null)
-                               throw new ArgumentNullException ("path");
-                       if (path.Length == 0)
-                               throw new ArgumentException ("An empty file name is not valid.");
-                       if (path.IndexOfAny (Path.InvalidPathChars) != -1)
-                               throw new ArgumentException ("Illegal characters in path.");
-                       if (Environment.IsRunningOnWindows) {
-                               int idx = path.IndexOf (':');
-                               if (idx >= 0 && idx != 1)
-                                       throw new ArgumentException ("path");
-                       }
-               }
-
-               internal MonoIOStat stat;
-               internal bool valid;
-       }
-}
index c84f4b705650e80b711389cb0e0ced183d7309d8..63756d190102372893732fd9e10aed7dabbf6526 100644 (file)
@@ -56,7 +56,9 @@ namespace System.IO
                ERROR_NO_MORE_FILES = 18,\r
        /*      ERROR_WRITE_PROTECT = 19,\r
                ERROR_BAD_UNIT = 20,\r
+       */\r
                ERROR_NOT_READY = 21,\r
+       /*\r
                ERROR_BAD_COMMAND = 22,\r
                ERROR_CRC = 23,\r
                ERROR_BAD_LENGTH = 24,\r
index a524b88ddd5fda1ac27e6cfb196b09c2f35307b1..c14420677ca909e8c5d5ff75cb0d0a2858979530 100644 (file)
@@ -1,11 +1,11 @@
-//\r
-// System.IO.MonoIOStat.cs: Idealized structure for file information.\r
-//\r
-// Author:\r
-//   Dan Lewis (dihlewis@yahoo.co.uk)\r
-//\r
-// (C) 2002\r
-//\r
+//
+// System.IO.MonoIOStat.cs: Idealized structure for file information.
+//
+// Author:
+//   Dan Lewis (dihlewis@yahoo.co.uk)
+//
+// (C) 2002
+//
 
 //
 // Copyright (C) 2004 Novell, Inc (http://www.novell.com)
 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 //
-\r
-using System;\r
-\r
-namespace System.IO\r
-{\r
-       internal struct MonoIOStat {\r
-               public FileAttributes Attributes;\r
-               public long Length;\r
-               public long CreationTime;\r
-               public long LastAccessTime;\r
-               public long LastWriteTime;\r
-       }\r
-}\r
+
+using System;
+using System.Runtime.InteropServices;
+
+namespace System.IO
+{
+       [StructLayout(LayoutKind.Sequential)]
+       internal struct MonoIOStat {
+               public FileAttributes fileAttributes;
+               public long Length;
+               public long CreationTime;
+               public long LastAccessTime;
+               public long LastWriteTime;
+       }
+}
index 9ac0e97545427ada48cdaaadfddd1f60b0eef086..fc62a4db6e3bff42240dfdca7c37c83252c7e266 100644 (file)
@@ -289,6 +289,11 @@ namespace System.IO {
                        return fullpath;
                }
 
+               internal static String GetFullPathInternal(String path)
+               {
+                       return InsecureGetFullPath (path);
+               }
+
 #if !MOBILE
                // http://msdn.microsoft.com/en-us/library/windows/desktop/aa364963%28v=vs.85%29.aspx
                [DllImport("Kernel32.dll", SetLastError = true, CharSet = CharSet.Unicode)]
@@ -488,7 +493,7 @@ namespace System.IO {
                                        f = new FileStream (path, FileMode.CreateNew, FileAccess.ReadWrite, FileShare.Read,
                                                            8192, false, (FileOptions) 1);
                                } catch (IOException ex){
-                                       if (ex.hresult != MonoIO.FileAlreadyExistsHResult || count ++ > 65536)
+                                       if (ex._HResult != MonoIO.FileAlreadyExistsHResult || count ++ > 65536)
                                                throw;
                                } catch (UnauthorizedAccessException ex) {
                                        if (count ++ > 65536)
@@ -871,5 +876,11 @@ namespace System.IO {
                                        throw new ArgumentException (parameterName);
                        }
                }
+
+               internal static string DirectorySeparatorCharAsString {
+                       get {
+                               return DirectorySeparatorStr;
+                       }
+               }
        }
 }
index 4d8b2ee34ba918eaaca8660fbcd515c1b552b850..b7ce6e0410a767355c9db8fcf9c9f0387ffd5f50 100644 (file)
@@ -40,120 +40,21 @@ using System.Text;
 
 namespace System.Reflection.Emit
 {
-       internal enum TypeKind : int {
-               SZARRAY = 0x1d,
-               ARRAY = 0x14
-       }
-
        [StructLayout (LayoutKind.Sequential)]
-       internal abstract class DerivedType : Type
+       abstract partial class SymbolType
        {
-               internal Type elementType;
+               internal Type m_baseType;
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
-               internal static extern void create_unmanaged_type (Type type);
+               static extern void create_unmanaged_type (Type type);
 
-               internal DerivedType (Type elementType)
+               internal SymbolType (Type elementType)
                {
-                       this.elementType = elementType;
+                       this.m_baseType = elementType;
                }
 
                internal abstract String FormatName (string elementName);
 
-               public override Type GetInterface (string name, bool ignoreCase)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override Type[] GetInterfaces ()
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override Type GetElementType ()
-               {
-                       return elementType;
-               }
-
-               public override EventInfo GetEvent (string name, BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override EventInfo[] GetEvents (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override FieldInfo GetField( string name, BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override FieldInfo[] GetFields (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override MemberInfo[] GetMembers (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               protected override MethodInfo GetMethodImpl (string name, BindingFlags bindingAttr, Binder binder,
-                                                            CallingConventions callConvention, Type[] types,
-                                                            ParameterModifier[] modifiers)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override MethodInfo[] GetMethods (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override Type GetNestedType (string name, BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override Type[] GetNestedTypes (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override PropertyInfo[] GetProperties (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               protected override PropertyInfo GetPropertyImpl (string name, BindingFlags bindingAttr, Binder binder,
-                                                                Type returnType, Type[] types, ParameterModifier[] modifiers)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               protected override ConstructorInfo GetConstructorImpl (BindingFlags bindingAttr,
-                                                                      Binder binder,
-                                                                      CallingConventions callConvention,
-                                                                      Type[] types,
-                                                                      ParameterModifier[] modifiers)
-               {
-                       throw new NotSupportedException ();
-               }
-
-
-               protected override TypeAttributes GetAttributeFlagsImpl ()
-               {
-                       /*LAMEIMPL MS just return the elementType.Attributes*/
-                       return elementType.Attributes; 
-               }
-
-               protected override bool HasElementTypeImpl ()
-               {
-                       return true;
-               }
-
                protected override bool IsArrayImpl ()
                {
                        return false;
@@ -164,60 +65,11 @@ namespace System.Reflection.Emit
                        return false;
                }
 
-               protected override bool IsCOMObjectImpl ()
-               {
-                       return false;
-               }
-
                protected override bool IsPointerImpl ()
                {
                        return false;
                }
 
-               protected override bool IsPrimitiveImpl ()
-               {
-                       return false;
-               }
-
-
-               public override ConstructorInfo[] GetConstructors (BindingFlags bindingAttr)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override object InvokeMember (string name, BindingFlags invokeAttr,
-                                                    Binder binder, object target, object[] args,
-                                                    ParameterModifier[] modifiers,
-                                                    CultureInfo culture, string[] namedParameters)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override InterfaceMapping GetInterfaceMap (Type interfaceType)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override bool IsInstanceOfType (object o)
-               {
-                       return false;
-               }
-
-               public override bool IsAssignableFrom (Type c)
-               {
-                       return false;
-               }
-
-               public override bool ContainsGenericParameters {
-                       get { return elementType.ContainsGenericParameters; }
-               }
-
-               //FIXME this should be handled by System.Type
-               public override Type MakeGenericType (params Type[] typeArguments)
-               {
-                       throw new NotSupportedException ();
-               }
-
                public override Type MakeArrayType ()
                {
                        return new ArrayType (this, 0);
@@ -242,59 +94,31 @@ namespace System.Reflection.Emit
 
                public override string ToString ()
                {
-                       return FormatName (elementType.ToString ());
-               }
-
-               public override GenericParameterAttributes GenericParameterAttributes {
-                       get { throw new NotSupportedException (); }
-               }
-
-               public override StructLayoutAttribute StructLayoutAttribute {
-                       get { throw new NotSupportedException (); }
-               }
-
-               public override Assembly Assembly {
-                       get { return elementType.Assembly; }
+                       return FormatName (m_baseType.ToString ());
                }
 
                public override string AssemblyQualifiedName {
                        get {
-                               string fullName = FormatName (elementType.FullName);
+                               string fullName = FormatName (m_baseType.FullName);
                                if (fullName == null)
                                        return null;
-                               return fullName + ", " + elementType.Assembly.FullName;
+                               return fullName + ", " + m_baseType.Assembly.FullName;
                        }
                }
 
 
                public override string FullName {
                        get {
-                               return FormatName (elementType.FullName);
+                               return FormatName (m_baseType.FullName);
                        }
                }
 
                public override string Name {
                        get {
-                               return FormatName (elementType.Name);
+                               return FormatName (m_baseType.Name);
                        }
                }
-
-               public override Guid GUID {
-                       get { throw new NotSupportedException (); }
-               }
-
-               public override Module Module {
-                       get { return elementType.Module; }
-               }
        
-               public override string Namespace {
-                       get { return elementType.Namespace; }
-               }
-
-               public override RuntimeTypeHandle TypeHandle {
-                       get { throw new NotSupportedException (); }
-               }
-
                public override Type UnderlyingSystemType {
                        get {
                                create_unmanaged_type (this);
@@ -302,31 +126,15 @@ namespace System.Reflection.Emit
                        }
                }
 
-               //MemberInfo
-               public override bool IsDefined (Type attributeType, bool inherit)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override object [] GetCustomAttributes (bool inherit)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public override object [] GetCustomAttributes (Type attributeType, bool inherit)
-               {
-                       throw new NotSupportedException ();
-               }
-
                internal override bool IsUserType {
                        get {
-                               return elementType.IsUserType;
+                               return m_baseType.IsUserType;
                        }
                }
        }
 
        [StructLayout (LayoutKind.Sequential)]
-       internal class ArrayType : DerivedType
+       internal class ArrayType : SymbolType
        {
                int rank;
 
@@ -342,7 +150,7 @@ namespace System.Reflection.Emit
 
                internal override Type InternalResolve ()
                {
-                       Type et = elementType.InternalResolve (); 
+                       Type et = m_baseType.InternalResolve (); 
                        if (rank == 0)
                                return et.MakeArrayType ();                     
                        return et.MakeArrayType (rank);
@@ -358,15 +166,6 @@ namespace System.Reflection.Emit
                        return (rank == 0) ? 1 : rank;
                }
 
-               public override Type BaseType {
-                       get { return typeof (System.Array); }
-               }
-
-               protected override TypeAttributes GetAttributeFlagsImpl ()
-               {
-                       return elementType.Attributes;
-               }
-
                internal override String FormatName (string elementName)
                {
                        if (elementName == null)
@@ -383,7 +182,7 @@ namespace System.Reflection.Emit
        }
 
        [StructLayout (LayoutKind.Sequential)]
-       internal class ByRefType : DerivedType
+       internal class ByRefType : SymbolType
        {
                internal ByRefType (Type elementType) : base (elementType)
                {
@@ -391,7 +190,7 @@ namespace System.Reflection.Emit
 
                internal override Type InternalResolve ()
                {
-                       return elementType.InternalResolve ().MakeByRefType (); 
+                       return m_baseType.InternalResolve ().MakeByRefType (); 
                }
 
                protected override bool IsByRefImpl ()
@@ -399,10 +198,6 @@ namespace System.Reflection.Emit
                        return true;
                }
 
-               public override Type BaseType {
-                       get { return typeof (Array); }
-               }
-
                internal override String FormatName (string elementName)
                {
                        if (elementName == null)
@@ -432,7 +227,7 @@ namespace System.Reflection.Emit
        }
 
        [StructLayout (LayoutKind.Sequential)]
-       internal class PointerType : DerivedType
+       internal class PointerType : SymbolType
        {
                internal PointerType (Type elementType) : base (elementType)
                {
@@ -440,7 +235,7 @@ namespace System.Reflection.Emit
 
                internal override Type InternalResolve ()
                {
-                       return elementType.InternalResolve ().MakePointerType (); 
+                       return m_baseType.InternalResolve ().MakePointerType (); 
                }
 
                protected override bool IsPointerImpl ()
@@ -448,10 +243,6 @@ namespace System.Reflection.Emit
                        return true;
                }
 
-               public override Type BaseType {
-                       get { return typeof(Array); }
-               }
-
                internal override String FormatName (string elementName)
                {
                        if (elementName == null)
index 8c6f92469380cc742e69ea9bce4f9d2d8003ba3c..ef2180fed03d619ec3a383dbbc2a46d5c8cb5b69 100644 (file)
@@ -296,6 +296,12 @@ namespace System.Reflection {
                                throw new InvalidOperationException ("Late bound operations cannot be performed on fields with types for which Type.ContainsGenericParameters is true.");
            }
 
+#if MOBILE
+               static int get_core_clr_security_level ()
+               {
+                       return 1;
+               }
+#else
                //seclevel { transparent = 0, safe-critical = 1, critical = 2}
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
                public extern int get_core_clr_security_level ();
@@ -311,5 +317,6 @@ namespace System.Reflection {
                public override bool IsSecuritySafeCritical {
                        get { return get_core_clr_security_level () == 1; }
                }
+#endif
        }
 }
index 544774d1786061abd71dcd490fc36a4c8e4dbf4b..04c0c5670863215cc7f35d8bec6d2db80fca9b72 100644 (file)
@@ -502,9 +502,16 @@ namespace System.Reflection {
                        return CustomAttributeData.GetCustomAttributes (this);
                }
 
+#if MOBILE
+               static int get_core_clr_security_level ()
+               {
+                       return 1;
+               }
+#else
                //seclevel { transparent = 0, safe-critical = 1, critical = 2}
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
                public extern int get_core_clr_security_level ();
+#endif
 
                public override bool IsSecurityTransparent {
                        get { return get_core_clr_security_level () == 0; }
@@ -751,5 +758,27 @@ namespace System.Reflection {
                public override IList<CustomAttributeData> GetCustomAttributesData () {
                        return CustomAttributeData.GetCustomAttributes (this);
                }
+
+#if MOBILE
+               static int get_core_clr_security_level ()
+               {
+                       return 1;
+               }
+#else
+               [MethodImplAttribute(MethodImplOptions.InternalCall)]
+               public extern int get_core_clr_security_level ();
+#endif
+
+               public override bool IsSecurityTransparent {
+                       get { return get_core_clr_security_level () == 0; }
+               }
+
+               public override bool IsSecurityCritical {
+                       get { return get_core_clr_security_level () > 0; }
+               }
+
+               public override bool IsSecuritySafeCritical {
+                       get { return get_core_clr_security_level () == 1; }
+               }
        }
 }
index 2256ebde0eab496d2dbbb03aaa04d723d1a1bdf7..ec83a3e0756b6f79737d2acb38b87f4ea11ba02b 100644 (file)
@@ -30,6 +30,7 @@
 //
 
 using System;
+using System.Threading;
 using System.Runtime.CompilerServices;
 using System.Runtime.InteropServices;
 
@@ -108,8 +109,17 @@ namespace System.Runtime.InteropServices
 
                public void Free()
                {
-                       FreeHandle(handle);
-                       handle = 0;
+                       // Copy the handle instance member to a local variable. This is required to prevent
+                       // race conditions releasing the handle.
+                       int local_handle = handle;
+
+                       // Free the handle if it hasn't already been freed.
+                       if (local_handle != 0 && Interlocked.CompareExchange (ref handle, 0, local_handle) == local_handle) {
+                               FreeHandle (local_handle);
+                       }
+                       else {
+                               throw new InvalidOperationException ("Handle is not initialized.");
+                       }
                }
                
                public static explicit operator IntPtr (GCHandle value)
@@ -120,7 +130,7 @@ namespace System.Runtime.InteropServices
                public static explicit operator GCHandle(IntPtr value)
                {
                        if (value == IntPtr.Zero)
-                               throw new ArgumentException ("GCHandle value cannot be zero");
+                               throw new InvalidOperationException ("GCHandle value cannot be zero");
                        if (!CheckCurrentDomain ((int)value))
                                throw new ArgumentException ("GCHandle value belongs to a different domain");
                        return new GCHandle (value);
index 8bed0815d260a9d15a98da78b35cdbbe2a62f6ba..24f15e3f980437e7877e372bf84a63afb6220ffb 100644 (file)
@@ -412,7 +412,7 @@ namespace System.Runtime.InteropServices
                        var errorInfo = new ManagedErrorInfo(e);
                        SetErrorInfo (0, errorInfo);
 
-                       return e.hresult;
+                       return e._HResult;
 #else                  
                        return -1;
 #endif
@@ -1591,7 +1591,7 @@ namespace System.Runtime.InteropServices
                                }
                        }
 
-                       if (info is ManagedErrorInfo && ((ManagedErrorInfo) info).Exception.hresult == errorCode) {
+                       if (info is ManagedErrorInfo && ((ManagedErrorInfo) info).Exception._HResult == errorCode) {
                                return ((ManagedErrorInfo) info).Exception;
                        }
 
diff --git a/mcs/class/corlib/System.Security.Cryptography.X509Certificates/INativeCertificateHelper.cs b/mcs/class/corlib/System.Security.Cryptography.X509Certificates/INativeCertificateHelper.cs
new file mode 100644 (file)
index 0000000..2d56ac1
--- /dev/null
@@ -0,0 +1,35 @@
+//
+// INativeCertificateHelper.cs
+//
+// Author:
+//       Martin Baulig <martin.baulig@xamarin.com>
+//
+// Copyright (c) 2016 Xamarin, Inc.
+//
+// Permission is hereby granted, free of charge, to any person obtaining a copy
+// of this software and associated documentation files (the "Software"), to deal
+// in the Software without restriction, including without limitation the rights
+// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+// copies of the Software, and to permit persons to whom the Software is
+// furnished to do so, subject to the following conditions:
+//
+// The above copyright notice and this permission notice shall be included in
+// all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+// THE SOFTWARE.
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       internal interface INativeCertificateHelper
+       {
+               X509CertificateImpl Import (byte[] data, string password, X509KeyStorageFlags flags);
+
+               X509CertificateImpl Import (X509Certificate cert);
+       }
+}
index 144997e573b63c0cb211a47596cdbb0e676228ac..135b270e508bb123f5f1226ee18710b2942347ca 100644 (file)
@@ -109,17 +109,44 @@ namespace System.Security.Cryptography.X509Certificates {
                        impl = X509Helper.InitFromHandle (handle);
                }
 
+               internal X509Certificate (X509CertificateImpl impl)
+               {
+                       if (impl == null)
+                               throw new ArgumentNullException ("impl");
+
+                       this.impl = X509Helper.InitFromCertificate (impl);
+               }
+
                public X509Certificate (System.Security.Cryptography.X509Certificates.X509Certificate cert) 
                {
                        if (cert == null)
                                throw new ArgumentNullException ("cert");
 
-                       X509Helper.ThrowIfContextInvalid (cert.impl);
-
-                       impl = X509Helper.InitFromCertificate (cert.impl);
+                       impl = X509Helper.InitFromCertificate (cert);
                        hideDates = false;
                }
 
+               internal void ImportHandle (X509CertificateImpl impl)
+               {
+                       Reset ();
+                       this.impl = impl;
+               }
+
+               internal X509CertificateImpl Impl {
+                       get {
+                               X509Helper.ThrowIfContextInvalid (impl);
+                               return impl;
+                       }
+               }
+
+               internal bool IsValid {
+                       get { return X509Helper.IsValid (impl); }
+               }
+
+               internal void ThrowIfContextInvalid ()
+               {
+                       X509Helper.ThrowIfContextInvalid (impl);
+               }
 
                // public methods
        
@@ -161,7 +188,7 @@ namespace System.Security.Cryptography.X509Certificates {
                                return null;
                        X509Helper.ThrowIfContextInvalid (impl);
 
-                       return impl.GetEffectiveDateString ().ToString ();
+                       return impl.GetValidFrom ().ToLocalTime ().ToString ();
                }
        
                // strangly there are no DateTime returning function
@@ -171,7 +198,7 @@ namespace System.Security.Cryptography.X509Certificates {
                                return null;
                        X509Helper.ThrowIfContextInvalid (impl);
 
-                       return impl.GetExpirationDateString ().ToString ();
+                       return impl.GetValidUntil ().ToLocalTime ().ToString ();
                }
        
                // well maybe someday there'll be support for PGP or SPKI ?
index e3dc5b36201f71a1dec2488dcea7effa4d3e8135..548bc5d93c08ec546441419ce1a0499805b2da5b 100644 (file)
@@ -37,6 +37,11 @@ namespace System.Security.Cryptography.X509Certificates
                        get;
                }
 
+               /*
+                * This is used in System.dll's OSX509Certificates.cs
+                */
+               public abstract IntPtr GetNativeAppleCertificate ();
+
                protected void ThrowIfContextInvalid ()
                {
                        if (!IsValid)
@@ -45,17 +50,15 @@ namespace System.Security.Cryptography.X509Certificates
 
                public abstract X509CertificateImpl Clone ();
 
-               public abstract string GetSubjectSummary ();
-
                public abstract string GetIssuerName (bool legacyV1Mode);
 
                public abstract string GetSubjectName (bool legacyV1Mode);
 
                public abstract byte[] GetRawCertData ();
 
-               public abstract DateTime GetEffectiveDateString ();
+               public abstract DateTime GetValidFrom ();
 
-               public abstract DateTime GetExpirationDateString ();
+               public abstract DateTime GetValidUntil ();
 
                byte[] cachedCertificateHash;
 
diff --git a/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs b/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
new file mode 100644 (file)
index 0000000..718aadc
--- /dev/null
@@ -0,0 +1,199 @@
+using System;
+using System.Text;
+using System.Runtime.InteropServices;
+using XamMac.CoreFoundation;
+using MX = Mono.Security.X509;
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       class X509CertificateImplApple : X509CertificateImpl
+       {
+               IntPtr handle;
+               X509CertificateImpl fallback;
+
+               public X509CertificateImplApple (IntPtr handle, bool owns)
+               {
+                       this.handle = handle;
+                       if (!owns)
+                               CFHelpers.CFRetain (handle);
+               }
+
+               public override bool IsValid {
+                       get { return handle != IntPtr.Zero; }
+               }
+
+               public override IntPtr Handle {
+                       get { return handle; }
+               }
+
+               public override IntPtr GetNativeAppleCertificate ()
+               {
+                       ThrowIfContextInvalid ();
+                       return handle;
+               }
+
+               public override X509CertificateImpl Clone ()
+               {
+                       ThrowIfContextInvalid ();
+                       return new X509CertificateImplApple (handle, false);
+               }
+
+               [DllImport (CFHelpers.SecurityLibrary)]
+               extern static IntPtr SecCertificateCopySubjectSummary (IntPtr cert);
+
+               [DllImport (CFHelpers.SecurityLibrary)]
+               extern static IntPtr SecCertificateCopyData (IntPtr cert);
+
+               public override byte[] GetRawCertData ()
+               {
+                       ThrowIfContextInvalid ();
+                       var data = SecCertificateCopyData (handle);
+                       if (data == IntPtr.Zero)
+                               throw new ArgumentException ("Not a valid certificate");
+
+                       try {
+                               return CFHelpers.FetchDataBuffer (data);
+                       } finally {
+                               CFHelpers.CFRelease (data);
+                       }
+               }
+
+               public string GetSubjectSummary ()
+               {
+                       ThrowIfContextInvalid ();
+                       IntPtr cfstr = SecCertificateCopySubjectSummary (handle);
+                       string ret = CFHelpers.FetchString (cfstr);
+                       CFHelpers.CFRelease (cfstr);
+                       return ret;
+               }
+
+               protected override byte[] GetCertHash (bool lazy)
+               {
+                       // FIXME: might just return 'null' when 'lazy' is true.
+                       ThrowIfContextInvalid ();
+                       SHA1 sha = SHA1.Create ();
+                       return sha.ComputeHash (GetRawCertData ());
+               }
+
+               public override bool Equals (X509CertificateImpl other, out bool result)
+               {
+                       var otherAppleImpl = other as X509CertificateImplApple;
+                       if (otherAppleImpl != null && otherAppleImpl.handle == handle) {
+                               result = true;
+                               return true;
+                       }
+
+                       result = false;
+                       return false;
+               }
+
+               void MustFallback ()
+               {
+                       ThrowIfContextInvalid ();
+                       if (fallback != null)
+                               return;
+                       var mxCert = new MX.X509Certificate (GetRawCertData ());
+                       fallback = new X509CertificateImplMono (mxCert);
+               }
+
+               public X509CertificateImpl FallbackImpl {
+                       get {
+                               MustFallback ();
+                               return fallback;
+                       }
+               }
+
+               public override string GetSubjectName (bool legacyV1Mode)
+               {
+                       return FallbackImpl.GetSubjectName (legacyV1Mode);
+               }
+
+               public override string GetIssuerName (bool legacyV1Mode)
+               {
+                       return FallbackImpl.GetIssuerName (legacyV1Mode);
+               }
+
+               public override DateTime GetValidFrom ()
+               {
+                       return FallbackImpl.GetValidFrom ();
+               }
+
+               public override DateTime GetValidUntil ()
+               {
+                       return FallbackImpl.GetValidUntil ();
+               }
+
+               public override string GetKeyAlgorithm ()
+               {
+                       return FallbackImpl.GetKeyAlgorithm ();
+               }
+
+               public override byte[] GetKeyAlgorithmParameters ()
+               {
+                       return FallbackImpl.GetKeyAlgorithmParameters ();
+               }
+
+               public override byte[] GetPublicKey ()
+               {
+                       return FallbackImpl.GetPublicKey ();
+               }
+
+               public override byte[] GetSerialNumber ()
+               {
+                       return FallbackImpl.GetSerialNumber ();
+               }
+
+               public override byte[] Export (X509ContentType contentType, byte[] password)
+               {
+                       ThrowIfContextInvalid ();
+
+                       switch (contentType) {
+                       case X509ContentType.Cert:
+                               return GetRawCertData ();
+                       case X509ContentType.Pfx: // this includes Pkcs12
+                               // TODO
+                               throw new NotSupportedException ();
+                       case X509ContentType.SerializedCert:
+                               // TODO
+                               throw new NotSupportedException ();
+                       default:
+                               string msg = Locale.GetText ("This certificate format '{0}' cannot be exported.", contentType);
+                               throw new CryptographicException (msg);
+                       }
+               }
+
+               public override string ToString (bool full)
+               {
+                       ThrowIfContextInvalid ();
+
+                       if (!full || fallback == null) {
+                               var summary = GetSubjectSummary ();
+                               return string.Format ("[X509Certificate: {0}]", summary);
+                       }
+
+                       string nl = Environment.NewLine;
+                       StringBuilder sb = new StringBuilder ();
+                       sb.AppendFormat ("[Subject]{0}  {1}{0}{0}", nl, GetSubjectName (false));
+
+                       sb.AppendFormat ("[Issuer]{0}  {1}{0}{0}", nl, GetIssuerName (false));
+                       sb.AppendFormat ("[Not Before]{0}  {1}{0}{0}", nl, GetValidFrom ().ToLocalTime ());
+                       sb.AppendFormat ("[Not After]{0}  {1}{0}{0}", nl, GetValidUntil ().ToLocalTime ());
+                       sb.AppendFormat ("[Thumbprint]{0}  {1}{0}", nl, X509Helper.ToHexString (GetCertHash ()));
+
+                       sb.Append (nl);
+                       return sb.ToString ();
+               }
+
+               protected override void Dispose (bool disposing)
+               {
+                       if (handle != IntPtr.Zero){
+                               CFHelpers.CFRelease (handle);
+                               handle = IntPtr.Zero;
+                       }
+                       if (fallback != null) {
+                               fallback.Dispose ();
+                               fallback = null;
+                       }
+               }
+       }
+}
index 85985c5d303cef3e3beebb05c1fb9f9c51eba7cd..fa152e97f919844f8b46992853d506f795542347 100644 (file)
@@ -34,7 +34,7 @@ using MX = Mono.Security.X509;
 
 namespace System.Security.Cryptography.X509Certificates
 {
-       class X509CertificateImplMono : X509CertificateImpl
+       sealed class X509CertificateImplMono : X509CertificateImpl
        {
                MX.X509Certificate x509;
 
@@ -51,6 +51,11 @@ namespace System.Security.Cryptography.X509Certificates
                        get { return IntPtr.Zero; }
                }
 
+               public override IntPtr GetNativeAppleCertificate ()
+               {
+                       return IntPtr.Zero;
+               }
+
                public override X509CertificateImpl Clone ()
                {
                        ThrowIfContextInvalid ();
@@ -66,12 +71,6 @@ namespace System.Security.Cryptography.X509Certificates
                                return MX.X501.ToString (x509.GetIssuerName (), true, ", ", true);
                }
 
-               public override string GetSubjectSummary ()
-               {
-                       ThrowIfContextInvalid ();
-                       return x509.SubjectName;
-               }
-
                public override string GetSubjectName (bool legacyV1Mode)
                {
                        ThrowIfContextInvalid ();
@@ -94,16 +93,16 @@ namespace System.Security.Cryptography.X509Certificates
                        return sha.ComputeHash (x509.RawData);
                }
 
-               public override DateTime GetEffectiveDateString ()
+               public override DateTime GetValidFrom ()
                {
                        ThrowIfContextInvalid ();
-                       return x509.ValidFrom.ToLocalTime ();
+                       return x509.ValidFrom;
                }
 
-               public override DateTime GetExpirationDateString ()
+               public override DateTime GetValidUntil ()
                {
                        ThrowIfContextInvalid ();
-                       return x509.ValidUntil.ToLocalTime ();
+                       return x509.ValidUntil;
                }
 
                public override bool Equals (X509CertificateImpl other, out bool result)
@@ -164,8 +163,8 @@ namespace System.Security.Cryptography.X509Certificates
                        StringBuilder sb = new StringBuilder ();
                        sb.AppendFormat ("[Subject]{0}  {1}{0}{0}", nl, GetSubjectName (false));
                        sb.AppendFormat ("[Issuer]{0}  {1}{0}{0}", nl, GetIssuerName (false));
-                       sb.AppendFormat ("[Not Before]{0}  {1}{0}{0}", nl, GetEffectiveDateString ());
-                       sb.AppendFormat ("[Not After]{0}  {1}{0}{0}", nl, GetExpirationDateString ());
+                       sb.AppendFormat ("[Not Before]{0}  {1}{0}{0}", nl, GetValidFrom ().ToLocalTime ());
+                       sb.AppendFormat ("[Not After]{0}  {1}{0}{0}", nl, GetValidUntil ().ToLocalTime ());
                        sb.AppendFormat ("[Thumbprint]{0}  {1}{0}", nl, X509Helper.ToHexString (GetCertHash ()));
                        sb.Append (nl);
                        return sb.ToString ();
diff --git a/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs b/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
new file mode 100644 (file)
index 0000000..7068882
--- /dev/null
@@ -0,0 +1,50 @@
+using System;
+using System.Runtime.InteropServices;
+using MX = Mono.Security.X509;
+using XamMac.CoreFoundation;
+
+namespace System.Security.Cryptography.X509Certificates
+{
+       static partial class X509Helper
+       {
+               public static X509CertificateImpl InitFromHandle (IntPtr handle)
+               {
+                       return new X509CertificateImplApple (handle, false);
+               }
+
+               public static X509CertificateImpl Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
+               {
+                       MX.X509Certificate x509;
+                       IntPtr handle;
+                       if (password == null) {
+                               handle = CFHelpers.CreateCertificateFromData (rawData);
+                               if (handle != IntPtr.Zero)
+                                       return new X509CertificateImplApple (handle, true);
+
+                               try {
+                                       x509 = new MX.X509Certificate (rawData);
+                               } catch (Exception e) {
+                                       try {
+                                               x509 = X509Helper.ImportPkcs12 (rawData, null);
+                                       } catch {
+                                               string msg = Locale.GetText ("Unable to decode certificate.");
+                                               // inner exception is the original (not second) exception
+                                               throw new CryptographicException (msg, e);
+                                       }
+                               }
+                       } else {
+                               // try PKCS#12
+                               try {
+                                       x509 = X509Helper.ImportPkcs12 (rawData, password);
+                               }
+                               catch {
+                                       // it's possible to supply a (unrequired/unusued) password
+                                       // fix bug #79028
+                                       x509 = new MX.X509Certificate (rawData);
+                               }
+                       }
+
+                       return new X509CertificateImplMono (x509);
+               }
+       }
+}
diff --git a/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.MonoTouch.opt.cs b/mcs/class/corlib/System.Security.Cryptography.X509Certificates/X509Helper.MonoTouch.opt.cs
deleted file mode 100644 (file)
index 19f1c4e..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#if MONOTOUCH || XAMMAC
-
-// this file is a shim to enable compiling monotouch profiles without mono-extensions
-namespace System.Security.Cryptography.X509Certificates
-{
-       static partial class X509Helper
-       {
-               public static X509CertificateImpl InitFromHandle (IntPtr handle)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               public static X509CertificateImpl Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
-               {
-                       throw new NotSupportedException ();
-               }
-       }
-}
-
-#endif
index dc73f5ad79d191f0497cfa62e20f0d15cf980e9d..1f3f1f83d1f9281914969e2139926fde093d3107 100644 (file)
@@ -30,6 +30,7 @@
 //
 using System;
 using System.Text;
+using System.Threading;
 using System.Runtime.InteropServices;
 #if !NET_2_1
 using System.Security.Permissions;
@@ -40,6 +41,14 @@ namespace System.Security.Cryptography.X509Certificates
 {
        static partial class X509Helper
        {
+               static INativeCertificateHelper nativeHelper;
+
+               internal static void InstallNativeHelper (INativeCertificateHelper helper)
+               {
+                       if (nativeHelper == null)
+                               Interlocked.CompareExchange (ref nativeHelper, helper, null);
+               }
+
 #if !NET_2_1
                // typedef struct _CERT_CONTEXT {
                //      DWORD                   dwCertEncodingType;
@@ -77,6 +86,14 @@ namespace System.Security.Cryptography.X509Certificates
                }
 #endif
 
+               public static X509CertificateImpl InitFromCertificate (X509Certificate cert)
+               {
+                       if (nativeHelper != null)
+                               return nativeHelper.Import (cert);
+
+                       return InitFromCertificate (cert.Impl);
+               }
+
                public static X509CertificateImpl InitFromCertificate (X509CertificateImpl impl)
                {
                        ThrowIfContextInvalid (impl);
@@ -134,6 +151,9 @@ namespace System.Security.Cryptography.X509Certificates
 #if !MONOTOUCH && !XAMMAC
                public static X509CertificateImpl Import (byte[] rawData, string password, X509KeyStorageFlags keyStorageFlags)
                {
+                       if (nativeHelper != null)
+                               return nativeHelper.Import (rawData, password, keyStorageFlags);
+
                        MX.X509Certificate x509;
                        if (password == null) {
                                try {
diff --git a/mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.cs b/mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.cs
new file mode 100644 (file)
index 0000000..554b206
--- /dev/null
@@ -0,0 +1,30 @@
+using System;
+
+namespace System.Text {
+
+       internal static partial class EncodingHelper {
+
+               static volatile Encoding utf8Encoding;
+
+               internal static Encoding UTF8 {
+                       get {
+                               if (utf8Encoding == null) {
+                                       lock (lockobj){
+                                               if (utf8Encoding == null){
+                                                       utf8Encoding = new UTF8Encoding (true, false);
+                                                       utf8Encoding.setReadOnly ();
+                                               }
+                                       }
+                               }
+
+                               return utf8Encoding;
+                       }
+               }
+
+               // The mobile profile has been default'ing to UTF8 since it's creation
+               internal static Encoding GetDefaultEncoding ()
+               {
+                       return UTF8;
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.opt.cs b/mcs/class/corlib/System.Text/EncodingHelper.MonoTouch.opt.cs
deleted file mode 100644 (file)
index 9aba0f6..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#if MONOTOUCH
-
-// this file is a shim to enable compiling monotouch profiles without mono-extensions
-namespace System.Text
-{
-       internal static partial class EncodingHelper
-       {
-               internal static Encoding GetDefaultEncoding ()
-               {
-                       throw new NotSupportedException ();
-               }
-       }
-}
-
-#endif
index c5cda6920d2edc3729e325bd3228629350ef94ae..b76c35d2d88324116507e97faef0a68db4969c08 100644 (file)
@@ -159,33 +159,33 @@ namespace System.Threading
 
                public static bool Wait(object obj, int millisecondsTimeout, bool exitContext) {
                        try {
-                               if (exitContext) {
-#if MONOTOUCH
-                                       throw new NotSupportedException ("exitContext == true is not supported");
-#else
+#if !DISABLE_REMOTING
+                               if (exitContext)
                                        SynchronizationAttribute.ExitContext ();
 #endif
-                               }
                                return Wait (obj, millisecondsTimeout);
                        }
                        finally {
-                               if (exitContext) SynchronizationAttribute.EnterContext ();
+#if !DISABLE_REMOTING
+                               if (exitContext)
+                                       SynchronizationAttribute.EnterContext ();
+#endif
                        }
                }
 
                public static bool Wait(object obj, TimeSpan timeout, bool exitContext) {
                        try {
-                               if (exitContext) {
-#if MONOTOUCH
-                                       throw new NotSupportedException ("exitContext == true is not supported");
-#else
+#if !DISABLE_REMOTING
+                               if (exitContext)
                                        SynchronizationAttribute.ExitContext ();
 #endif
-                               }
                                return Wait (obj, timeout);
                        }
                        finally {
-                               if (exitContext) SynchronizationAttribute.EnterContext ();
+#if !DISABLE_REMOTING
+                               if (exitContext)
+                                       SynchronizationAttribute.EnterContext ();
+#endif
                        }
                }
 
index 019647bc0bd85170bb18b74ae176517b3f1b1ad9..f09b9fe7e551c33a006f27bf3fa1300258b73e04 100644 (file)
@@ -47,16 +47,13 @@ namespace System.Threading
 
                static int WaitMultiple(WaitHandle[] waitHandles, int millisecondsTimeout, bool exitContext, bool WaitAll)
                {
-#if MONOTOUCH
-                       if (exitContext)
-                               throw new NotSupportedException ("exitContext == true is not supported");
-#endif
-
                        int release_last = -1;
 
                        try {
+#if !DISABLE_REMOTING
                                if (exitContext)
                                        SynchronizationAttribute.ExitContext ();
+#endif
 
                                for (int i = 0; i < waitHandles.Length; ++i) {
                                        try {
@@ -70,51 +67,52 @@ namespace System.Threading
                                }
 
                                if (WaitAll)
-                                       return WaitAll_internal (waitHandles, millisecondsTimeout, exitContext);
+                                       return WaitAll_internal (waitHandles, millisecondsTimeout);
                                else
-                                       return WaitAny_internal (waitHandles, millisecondsTimeout, exitContext);
+                                       return WaitAny_internal (waitHandles, millisecondsTimeout);
                        } finally {
                                for (int i = release_last; i >= 0; --i) {
                                        waitHandles [i].SafeWaitHandle.DangerousRelease ();
                                }
 
+#if !DISABLE_REMOTING
                                if (exitContext)
                                        SynchronizationAttribute.EnterContext ();
+#endif
                        }
                }
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
-               private static extern int WaitAll_internal(WaitHandle[] handles, int ms, bool exitContext);
+               private static extern int WaitAll_internal(WaitHandle[] handles, int ms);
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
-               private static extern int WaitAny_internal(WaitHandle[] handles, int ms, bool exitContext);
+               private static extern int WaitAny_internal(WaitHandle[] handles, int ms);
 
                static int WaitOneNative (SafeHandle waitableSafeHandle, uint millisecondsTimeout, bool hasThreadAffinity, bool exitContext)
                {
-#if MONOTOUCH
-                       if (exitContext)
-                               throw new NotSupportedException ("exitContext == true is not supported");
-#endif
-
                        bool release = false;
                        try {
+#if !DISABLE_REMOTING
                                if (exitContext)
                                        SynchronizationAttribute.ExitContext ();
+#endif
 
                                waitableSafeHandle.DangerousAddRef (ref release);
 
-                               return WaitOne_internal (waitableSafeHandle.DangerousGetHandle (), (int) millisecondsTimeout, exitContext);
+                               return WaitOne_internal (waitableSafeHandle.DangerousGetHandle (), (int) millisecondsTimeout);
                        } finally {
                                if (release)
                                        waitableSafeHandle.DangerousRelease ();
 
+#if !DISABLE_REMOTING
                                if (exitContext)
                                        SynchronizationAttribute.EnterContext ();
+#endif
                        }
                }
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
-               static extern int WaitOne_internal(IntPtr handle, int ms, bool exitContext);
+               static extern int WaitOne_internal(IntPtr handle, int ms);
 
                static int SignalAndWaitOne (SafeWaitHandle waitHandleToSignal,SafeWaitHandle waitHandleToWaitOn, int millisecondsTimeout, bool hasThreadAffinity,  bool exitContext)
                {
@@ -123,7 +121,7 @@ namespace System.Threading
                                waitHandleToSignal.DangerousAddRef (ref releaseHandleToSignal);
                                waitHandleToWaitOn.DangerousAddRef (ref releaseHandleToWaitOn);
 
-                               return SignalAndWait_Internal (waitHandleToSignal.DangerousGetHandle (), waitHandleToWaitOn.DangerousGetHandle (), millisecondsTimeout, exitContext);
+                               return SignalAndWait_Internal (waitHandleToSignal.DangerousGetHandle (), waitHandleToWaitOn.DangerousGetHandle (), millisecondsTimeout);
                        } finally {
                                if (releaseHandleToSignal)
                                        waitHandleToSignal.DangerousRelease ();
@@ -133,6 +131,6 @@ namespace System.Threading
                }
 
                [MethodImplAttribute(MethodImplOptions.InternalCall)]
-               static extern int SignalAndWait_Internal (IntPtr toSignal, IntPtr toWaitOn, int ms, bool exitContext);
+               static extern int SignalAndWait_Internal (IntPtr toSignal, IntPtr toWaitOn, int ms);
        }
 }
index aee50509f8f299f121260c1a47ac362951d5d504..f75547ab13d55a425298a88f431b885aa0462a08 100644 (file)
@@ -96,11 +96,6 @@ namespace System
 
                static Console ()
                {
-#if NET_2_1
-                       Encoding inputEncoding;
-                       Encoding outputEncoding;
-#endif
-
                        if (Environment.IsRunningOnWindows) {
                                //
                                // On Windows, follow the Windows tradition
@@ -524,7 +519,6 @@ namespace System
 
 #endif
 
-#if !NET_2_1
                // FIXME: Console should use these encodings when changed
                static Encoding inputEncoding;
                static Encoding outputEncoding;
@@ -545,6 +539,7 @@ namespace System
                        }
                }
 
+#if !NET_2_1
                public static ConsoleColor BackgroundColor {
                        get { return ConsoleDriver.BackgroundColor; }
                        set { ConsoleDriver.BackgroundColor = value; }
diff --git a/mcs/class/corlib/System/Environment.MonoTouch.opt.cs b/mcs/class/corlib/System/Environment.MonoTouch.opt.cs
deleted file mode 100644 (file)
index d45de30..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-#if MONOTOUCH
-
-// this file is a shim to enable compiling monotouch profiles without mono-extensions
-namespace System
-{
-       public static partial class Environment
-       {
-               public static string GetFolderPath(SpecialFolder folder, SpecialFolderOption option)
-               {
-                       throw new NotSupportedException ();
-               }
-
-               internal static string UnixGetFolderPath (SpecialFolder folder, SpecialFolderOption option)
-               {
-                       throw new NotSupportedException ();
-               }
-       }
-}
-
-#endif
index 70a4dea80df5d68f1a7de17fc2dfde0121e99606..73fef7906bb639c401e1f481c212ddd2a20d0e5c 100644 (file)
@@ -57,7 +57,7 @@ namespace System {
                 * of icalls, do not require an increment.
                 */
 #pragma warning disable 169
-               private const int mono_corlib_version = 143;
+               private const int mono_corlib_version = 146;
 #pragma warning restore 169
 
                [ComVisible (true)]
@@ -985,6 +985,19 @@ namespace System {
                {
 
                }
+
+               // Copied from referencesource Environment
+               internal static String GetStackTrace(Exception e, bool needFileInfo)
+               {
+                       System.Diagnostics.StackTrace st;
+                       if (e == null)
+                               st = new System.Diagnostics.StackTrace(needFileInfo);
+                       else
+                               st = new System.Diagnostics.StackTrace(e, needFileInfo);
+
+                       // Do not include a trailing newline for backwards compatibility
+                       return st.ToString( System.Diagnostics.StackTrace.TraceFormat.Normal );
+               }
        }
 }
 
diff --git a/mcs/class/corlib/System/Environment.iOS.cs b/mcs/class/corlib/System/Environment.iOS.cs
new file mode 100644 (file)
index 0000000..04ad76d
--- /dev/null
@@ -0,0 +1,148 @@
+// Copyright 2014 Xamarin Inc.
+
+// note: or older hack to give the Documents (or Library) directories 
+
+using System.IO;
+using System.Runtime.InteropServices;
+
+namespace System {
+
+       public static partial class Environment {
+
+               static string ns_document;
+               static string ns_library;
+
+               [DllImport ("__Internal")]
+               extern static string xamarin_GetFolderPath (int folder);
+
+               static string NSDocumentDirectory {
+                       get {
+                               if (ns_document == null) {
+#if MONOTOUCH_TV
+                                       // The "normal" NSDocumentDirectory is a read-only directory on tvOS
+                                       // and that breaks a lot of assumptions in the runtime and the BCL
+                                       // to avoid this we relocate the Documents directory under Caches
+                                       ns_document = Path.Combine (NSLibraryDirectory, "Caches", "Documents");
+                                       if (!Directory.Exists (ns_document))
+                                               Directory.CreateDirectory (ns_document);
+#else
+                                       ns_document = xamarin_GetFolderPath (/* NSDocumentDirectory */ 9);
+#endif
+                               }
+                               return ns_document;
+                       }
+               }
+
+               // Various user-visible documentation, support, and configuration files
+               static string NSLibraryDirectory {
+                       get {
+                               if (ns_library == null)
+                                       ns_library = xamarin_GetFolderPath (/* NSLibraryDirectory */ 5);
+                               return ns_library;
+                       }
+               }
+
+               public static string GetFolderPath (SpecialFolder folder, SpecialFolderOption option)
+               {
+                       return UnixGetFolderPath (folder, option);
+               }
+
+               // needed by our BCL, e.g. IsolatedStorageFile.cs
+               internal static string UnixGetFolderPath (SpecialFolder folder, SpecialFolderOption option)
+               {
+                       var dir = iOSGetFolderPath (folder);
+                       if ((option == SpecialFolderOption.Create) && !Directory.Exists (dir))
+                               Directory.CreateDirectory (dir);
+                       return dir;
+               }
+
+               internal static string iOSGetFolderPath (SpecialFolder folder)
+               {
+                       switch (folder) {
+                       case SpecialFolder.MyComputer:
+                       case SpecialFolder.Programs:
+                       case SpecialFolder.SendTo:
+                       case SpecialFolder.StartMenu:
+                       case SpecialFolder.Startup:
+                       case SpecialFolder.Cookies:
+                       case SpecialFolder.History:
+                       case SpecialFolder.Recent:
+                       case SpecialFolder.CommonProgramFiles:
+                       case SpecialFolder.System:
+                       case SpecialFolder.NetworkShortcuts:
+                       case SpecialFolder.CommonStartMenu:
+                       case SpecialFolder.CommonPrograms:
+                       case SpecialFolder.CommonStartup:
+                       case SpecialFolder.CommonDesktopDirectory:
+                       case SpecialFolder.PrinterShortcuts:
+                       case SpecialFolder.Windows:
+                       case SpecialFolder.SystemX86:
+                       case SpecialFolder.ProgramFilesX86:
+                       case SpecialFolder.CommonProgramFilesX86:
+                       case SpecialFolder.CommonDocuments:
+                       case SpecialFolder.CommonAdminTools:
+                       case SpecialFolder.AdminTools:
+                       case SpecialFolder.CommonMusic:
+                       case SpecialFolder.CommonPictures:
+                       case SpecialFolder.CommonVideos:
+                       case SpecialFolder.LocalizedResources:
+                       case SpecialFolder.CommonOemLinks:
+                       case SpecialFolder.CDBurning:
+                               return String.Empty;
+                       
+                       // personal == ~
+                       case SpecialFolder.Personal:
+                       case SpecialFolder.LocalApplicationData:
+                               return NSDocumentDirectory;
+
+                       case SpecialFolder.ApplicationData:
+                               // note: at first glance that looked like a good place to return NSLibraryDirectory 
+                               // but it would break isolated storage for existing applications
+                               return Path.Combine (NSDocumentDirectory, ".config");
+
+                       case SpecialFolder.Resources:
+                               return NSLibraryDirectory; // older (8.2 and previous) would return String.Empty
+
+                       case SpecialFolder.Desktop:
+                       case SpecialFolder.DesktopDirectory:
+                               return Path.Combine (NSDocumentDirectory, "Desktop");
+
+                       case SpecialFolder.MyMusic:
+                               return Path.Combine (NSDocumentDirectory, "Music");
+
+                       case SpecialFolder.MyPictures:
+                               return Path.Combine (NSDocumentDirectory, "Pictures");
+
+                       case SpecialFolder.Templates:
+                               return Path.Combine (NSDocumentDirectory, "Templates");
+
+                       case SpecialFolder.MyVideos:
+                               return Path.Combine (NSDocumentDirectory, "Videos");
+
+                       case SpecialFolder.CommonTemplates:
+                               return "/usr/share/templates";
+
+                       case SpecialFolder.Fonts:
+                               return Path.Combine (NSDocumentDirectory, ".fonts");
+
+                       case SpecialFolder.Favorites:
+                               return Path.Combine (NSLibraryDirectory, "Favorites");
+
+                       case SpecialFolder.ProgramFiles:
+                               return "/Applications";
+
+                       case SpecialFolder.InternetCache:
+                               return Path.Combine (NSLibraryDirectory, "Caches");
+
+                       case SpecialFolder.UserProfile:
+                               return internalGetHome ();
+
+                       case SpecialFolder.CommonApplicationData:
+                               return "/usr/share";
+
+                       default:
+                               throw new ArgumentException ("Invalid SpecialFolder");
+                       }
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/class/corlib/System/Exception.cs b/mcs/class/corlib/System/Exception.cs
deleted file mode 100644 (file)
index 7b6b492..0000000
+++ /dev/null
@@ -1,336 +0,0 @@
-//
-// System.Exception.cs
-//
-// Author:
-//   Miguel de Icaza (miguel@ximian.com)
-//   Patrik Torstensson
-//
-// (C) Ximian, Inc.  http://www.ximian.com
-// Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
-//
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System.Collections;
-using System.Collections.Generic;
-using System.Diagnostics;
-using System.Reflection;
-using System.Text;
-using System.Runtime.InteropServices;
-using System.Runtime.CompilerServices;
-using System.Runtime.Serialization;
-using System.Security.Permissions;
-
-namespace System
-{
-       [Serializable]
-       [ComVisible(true)]
-       [ComDefaultInterface (typeof (_Exception))]
-       [ClassInterface (ClassInterfaceType.None)]
-       [StructLayout (LayoutKind.Sequential)]
-#if MOBILE
-       public class Exception : ISerializable
-#else
-       public class Exception : ISerializable, _Exception
-#endif
-       {
-#pragma warning disable 169, 649
-               #region Sync with object-internals.h
-               /* Stores the IPs and the generic sharing infos
-                  (vtable/MRGCTX) of the frames. */
-               IntPtr [] trace_ips;
-               Exception inner_exception;
-               internal string _message;
-               string help_link;
-               string class_name;
-               string stack_trace;
-               // formerly known as remote_stack_trace (see #425512):
-               string _remoteStackTraceString;
-               int remote_stack_index;
-               internal int hresult = -2146233088;
-               string source;
-               IDictionary _data;
-               internal StackTrace[] captured_traces;
-               IntPtr[] native_trace_ips;
-               object dynamic_methods;
-               #endregion
-#pragma warning restore 169, 649
-
-               /* Don't add fields here, the runtime depends on the layout of subclasses */
-
-               public Exception ()
-               {
-               }
-
-               public Exception (string message)
-               {
-                       this._message = message;
-               }
-
-               protected Exception (SerializationInfo info, StreamingContext context)
-               {
-                       if (info == null)
-                               throw new ArgumentNullException ("info");
-
-                       class_name          = info.GetString ("ClassName");
-                       _message             = info.GetString ("Message");
-                       help_link           = info.GetString ("HelpURL");
-                       stack_trace         = info.GetString ("StackTraceString");
-                       _remoteStackTraceString  = info.GetString ("RemoteStackTraceString");
-                       remote_stack_index  = info.GetInt32  ("RemoteStackIndex");
-                       hresult             = info.GetInt32  ("HResult");
-                       source              = info.GetString ("Source");
-                       inner_exception     = (Exception) info.GetValue ("InnerException", typeof (Exception));
-
-                       try {
-                               _data = (IDictionary) info.GetValue ("Data", typeof (IDictionary));
-                       } catch (SerializationException) {
-                               // member did not exist in .NET 1.x
-                       }
-               }
-
-               public Exception (string message, Exception innerException)
-               {
-                       inner_exception = innerException;
-                       this._message = message;
-               }
-
-               public Exception InnerException {
-                       get { return inner_exception; }
-               }
-
-               public virtual string HelpLink {
-                       get { return help_link; }
-                       set { help_link = value; }
-               }
-
-               public int HResult {
-                       get { return hresult; }
-                       protected set { hresult = value; }
-               }
-               
-               internal void SetErrorCode(int hr)
-               {
-                       HResult = hr;
-               }
-
-               internal void SetMessage (string s)
-               {
-                       _message = s;
-               }
-
-               internal void SetStackTrace (string s)
-               {
-                       stack_trace = s;
-               }
-
-               string ClassName {
-                       get {
-                               if (class_name == null)
-                                       class_name = GetType ().ToString ();
-                               return class_name;
-                       }
-               }
-
-               public virtual string Message {
-                       get {
-                               if (_message == null)
-                                       _message = string.Format (Locale.GetText ("Exception of type '{0}' was thrown."),
-                                               ClassName);
-
-                               return _message;
-                       }
-               }
-               
-               [MonoTODO]
-               protected event EventHandler<SafeSerializationEventArgs> SerializeObjectState {
-                       add {
-                       }
-                       remove {
-                       }
-               }
-
-               public virtual string Source {
-                       get {
-                               if (source == null) {
-                                       StackTrace st = new StackTrace (this, true);
-                                       if (st.FrameCount > 0) {
-                                               StackFrame sf = st.GetFrame (0);
-                                               if (st != null) {
-                                                       MethodBase method = sf.GetMethod ();
-                                                       if (method != null) {
-                                                               source = method.DeclaringType.Assembly.UnprotectedGetName ().Name;
-                                                       }
-                                               }
-                                       }
-                               }
-
-                               // source can be null
-                               return source;
-                       }
-
-                       set {
-                               source = value;
-                       }
-               }
-
-               public virtual string StackTrace {
-                       get {
-                               if (stack_trace != null)
-                                       return stack_trace;
-
-                               if (trace_ips == null)
-                                       /* Not thrown yet */
-                                       return null;
-
-                               StackTrace st = new StackTrace (this, 0, true);
-                               return stack_trace = st.ToString ();
-                       }
-               }
-
-               public MethodBase TargetSite {
-                       get {
-                               StackTrace st = new StackTrace (this, true);
-                               if (st.FrameCount > 0)
-                                       return st.GetFrame (0).GetMethod ();
-                               
-                               return null;
-                       }
-               }
-
-               public virtual IDictionary Data {
-                       get {
-                               if (_data == null) {
-                                       // default to empty dictionary
-                                       _data = new Dictionary<object, object> ();
-                               }
-                               return _data;
-                       }
-               }
-
-               public virtual Exception GetBaseException ()
-               {
-                       Exception inner = inner_exception;
-                               
-                       while (inner != null)
-                       {
-                               if (inner.InnerException != null)
-                                       inner = inner.InnerException;
-                               else
-                                       return inner;
-                       }
-
-                       return this;
-               }
-
-               [SecurityPermission (SecurityAction.LinkDemand, SerializationFormatter = true)]
-               public virtual void GetObjectData (SerializationInfo info, StreamingContext context)
-               {
-                       if (info == null)
-                               throw new ArgumentNullException ("info");
-
-                       info.AddValue ("ClassName", ClassName);
-                       info.AddValue ("Message", _message);
-                       info.AddValue ("InnerException", inner_exception, typeof (Exception));
-                       info.AddValue ("HelpURL", help_link);
-                       info.AddValue ("StackTraceString", StackTrace);
-                       info.AddValue ("RemoteStackTraceString", _remoteStackTraceString);
-                       info.AddValue ("RemoteStackIndex", remote_stack_index);
-                       info.AddValue ("HResult", hresult);
-                       info.AddValue ("Source", Source);
-                       info.AddValue ("ExceptionMethod", null);
-                       info.AddValue ("Data", _data, typeof (IDictionary));
-               }
-
-               public override string ToString ()
-               {
-                       System.Text.StringBuilder result = new System.Text.StringBuilder (ClassName);
-                       result.Append (": ").Append (Message);
-
-                       if (null != _remoteStackTraceString)
-                               result.Append (_remoteStackTraceString);
-                               
-                       if (inner_exception != null) 
-                       {
-                               result.Append (" ---> ").Append (inner_exception.ToString ());
-                               result.Append (Environment.NewLine);
-                               result.Append (Locale.GetText ("  --- End of inner exception stack trace ---"));
-                       }
-
-                       if (StackTrace != null)
-                               result.Append (Environment.NewLine).Append (StackTrace);
-                       return result.ToString();
-               }
-
-               internal Exception FixRemotingException ()
-               {
-                       string message = (0 == remote_stack_index) ?
-                               Locale.GetText ("{0}{0}Server stack trace: {0}{1}{0}{0}Exception rethrown at [{2}]: {0}") :
-                               Locale.GetText ("{1}{0}{0}Exception rethrown at [{2}]: {0}");
-                       string tmp = String.Format (message, Environment.NewLine, StackTrace, remote_stack_index);
-
-                       _remoteStackTraceString = tmp;
-                       remote_stack_index++;
-
-                       stack_trace = null;
-
-                       return this;
-               }
-
-               // For ExceptionDispatchInfo
-               internal void RestoreExceptionDispatchInfo (System.Runtime.ExceptionServices.ExceptionDispatchInfo exceptionDispatchInfo)
-               {
-                       captured_traces = (StackTrace[]) exceptionDispatchInfo.BinaryStackTraceArray;
-                       trace_ips = null;
-                       stack_trace = null;
-               }
-
-               //
-               // The documentation states that this is available in 1.x,
-               // but it was not available (MemberRefing this would fail)
-               // and it states the signature is `override sealed', but the
-               // correct value is `newslot' 
-               //
-               public new Type GetType ()
-               {
-                       return base.GetType ();
-               }
-
-               internal enum ExceptionMessageKind
-               {
-                       ThreadAbort = 1,
-                       ThreadInterrupted = 2,
-                       OutOfMemory = 3
-               }
-
-               internal static String GetMessageFromNativeResources (ExceptionMessageKind kind)
-               {
-                       switch (kind) {
-                       case ExceptionMessageKind.ThreadAbort:
-                               return "";
-                       case ExceptionMessageKind.ThreadInterrupted:
-                               return "";
-                       case ExceptionMessageKind.OutOfMemory:
-                               return "Out of memory";
-                       }
-                       return "";
-               }
-       }
-}
diff --git a/mcs/class/corlib/System/Guid.MonoTouch.cs b/mcs/class/corlib/System/Guid.MonoTouch.cs
new file mode 100644 (file)
index 0000000..714bdb6
--- /dev/null
@@ -0,0 +1,25 @@
+#if MONOTOUCH && FULL_AOT_RUNTIME
+
+using Crimson.CommonCrypto;
+
+namespace System
+{
+       partial struct Guid
+       {
+               public static Guid NewGuid ()
+               {
+                       byte[] b = new byte [16];
+                       Cryptor.GetRandom (b);
+
+                       Guid res = new Guid (b);
+                       // Mask in Variant 1-0 in Bit[7..6]
+                       res._d = (byte) ((res._d & 0x3fu) | 0x80u);
+                       // Mask in Version 4 (random based Guid) in Bits[15..13]
+                       res._c = (short) ((res._c & 0x0fffu) | 0x4000u);
+
+                       return res;
+               }
+       }
+}
+
+#endif
\ No newline at end of file
diff --git a/mcs/class/corlib/System/Guid.MonoTouch.opt.cs b/mcs/class/corlib/System/Guid.MonoTouch.opt.cs
deleted file mode 100644 (file)
index beb6a3a..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-#if MONOTOUCH && FULL_AOT_RUNTIME
-
-// this file is a shim to enable compiling monotouch profiles without mono-extensions
-namespace System
-{
-       partial struct Guid
-       {
-               public static Guid NewGuid ()
-               {
-                       throw new NotSupportedException ();
-               }
-       }
-}
-
-#endif
diff --git a/mcs/class/corlib/System/NotSupportedException.iOS.cs b/mcs/class/corlib/System/NotSupportedException.iOS.cs
new file mode 100644 (file)
index 0000000..c18b3d6
--- /dev/null
@@ -0,0 +1,13 @@
+namespace System {
+
+       public partial class NotSupportedException {
+
+               // Avoid having the linker generate this method for every linked build
+               // It also fix #30075 where --linkskip=mscorlib means that method could not be added
+               // but still referenced from other assemblies
+               internal static Exception LinkedAway ()
+               {
+                       return new NotSupportedException ("Linked Away");
+               }
+       }
+}
\ No newline at end of file
index 9ad485e07cd52b254e1265c18d95f3e0a2fc9c4d..3cf08ae352089a434b6c8ac006bf6ab5e9c6e1a3 100644 (file)
@@ -218,7 +218,7 @@ namespace System {
                        if (typeName == null)
                                throw new ArgumentNullException ("typeName");
 
-                       TypeSpec res = Parse (typeName, ref pos, false, false);
+                       TypeSpec res = Parse (typeName, ref pos, false, true);
                        if (pos < typeName.Length)
                                throw new ArgumentException ("Count not parse the whole type name", "typeName");
                        return res;
@@ -287,7 +287,7 @@ namespace System {
                {
                        Assembly asm = null;
                        if (assemblyResolver == null && typeResolver == null)
-                               return Type.GetType (name.DisplayName, throwOnError, ignoreCase);
+                               return Type.GetType (DisplayFullName, throwOnError, ignoreCase);
 
                        if (assembly_name != null) {
                                if (assemblyResolver != null)
@@ -376,6 +376,12 @@ namespace System {
                        pos = p;
                }
 
+               static void BoundCheck (int idx, string s)
+               {
+                       if (idx >= s.Length)
+                               throw new ArgumentException ("Invalid generic arguments spec", "typeName");
+               }
+
                static TypeIdentifier ParsedTypeIdentifier (string displayName)
                {
                        return TypeIdentifiers.FromDisplay(displayName);
@@ -383,6 +389,17 @@ namespace System {
 
                static TypeSpec Parse (string name, ref int p, bool is_recurse, bool allow_aqn)
                {
+                       // Invariants:
+                       //  - On exit p, is updated to pos the current unconsumed character.
+                       //
+                       //  - The callee peeks at but does not consume delimiters following
+                       //    recurisve parse (so for a recursive call like the args of "Foo[P,Q]"
+                       //    we'll return with p either on ',' or on ']'.  If the name was aqn'd
+                       //    "Foo[[P,assmblystuff],Q]" on return p with be on the ']' just
+                       //    after the "assmblystuff")
+                       //
+                       //  - If allow_aqn is True, assembly qualification is optional.
+                       //    If allow_aqn is False, assembly qualification is prohibited.
                        int pos = p;
                        int name_start;
                        bool in_modifiers = false;
@@ -450,18 +467,24 @@ namespace System {
                                                data.AddModifier (new PointerSpec(pointer_level));
                                                break;
                                        case ',':
-                                               if (is_recurse) {
+                                               if (is_recurse && allow_aqn) {
                                                        int end = pos;
                                                        while (end < name.Length && name [end] != ']')
                                                                ++end;
                                                        if (end >= name.Length)
                                                                throw new ArgumentException ("Unmatched ']' while parsing generic argument assembly name");
                                                        data.assembly_name = name.Substring (pos + 1, end - pos - 1).Trim ();
-                                                       p = end + 1;
+                                                       p = end;
                                                        return data;                                            
                                                }
-                                               data.assembly_name = name.Substring (pos + 1).Trim ();
-                                               pos = name.Length;
+                                               if (is_recurse) {
+                                                       p = pos;
+                                                       return data;
+                                               }
+                                               if (allow_aqn) {
+                                                       data.assembly_name = name.Substring (pos + 1).Trim ();
+                                                       pos = name.Length;
+                                               }
                                                break;
                                        case '[':
                                                if (data.is_byref)
@@ -482,11 +505,17 @@ namespace System {
                                                                if (aqn)
                                                                        ++pos; //skip '[' to the start of the type
                                                                args.Add (Parse (name, ref pos, true, aqn));
-                                                               if (pos >= name.Length)
-                                                                       throw new ArgumentException ("Invalid generic arguments spec", "typeName");
+                                                               BoundCheck (pos, name);
+                                                               if (aqn) {
+                                                                       if (name [pos] == ']')
+                                                                               ++pos;
+                                                                       else
+                                                                               throw new ArgumentException ("Unclosed assembly-qualified type name at " + name[pos], "typeName");
+                                                                       BoundCheck (pos, name);
+}
 
                                                                if (name [pos] == ']')
-                                                                               break;
+                                                                       break;
                                                                if (name [pos] == ',')
                                                                        ++pos; // skip ',' to the start of the next arg
                                                                else
@@ -523,7 +552,7 @@ namespace System {
                                                break;
                                        case ']':
                                                if (is_recurse) {
-                                                       p = pos + 1;
+                                                       p = pos;
                                                        return data;
                                                }
                                                throw new ArgumentException ("Unmatched ']'", "typeName");
index a772d0fef9791888bd00475df9459c80dc2cc4d6..2e7e6066af533f349baeb1462d36c468c53ac937 100644 (file)
@@ -63,6 +63,9 @@ namespace System
                #endregion
 #pragma warning restore 169
 
+               // keep a reference to the proxy so it doesn't get garbage collected before the RCW
+               ComInteropProxy proxy;
+
                [MethodImplAttribute (MethodImplOptions.InternalCall)]
                internal static extern __ComObject CreateRCW (Type t);
 
@@ -71,10 +74,13 @@ namespace System
 
                ~__ComObject ()
                {       
-                       if (synchronization_context != null)
-                               synchronization_context.Post ((state) => ReleaseInterfaces (), this);
-                       else
-                               ReleaseInterfaces ();                           
+                       if (hash_table != IntPtr.Zero) {
+                               if (synchronization_context != null)
+                                       synchronization_context.Post ((state) => ReleaseInterfaces (), this);
+                               else
+                                       ReleaseInterfaces ();
+                       }
+                       proxy = null;
                }
 
                public __ComObject ()
@@ -86,14 +92,22 @@ namespace System
                        Initialize (t);
                }
 
-               internal __ComObject (IntPtr pItf)
+               internal __ComObject (IntPtr pItf, ComInteropProxy p)
                {
+                       proxy = p;
                        InitializeApartmentDetails ();
                        Guid iid = IID_IUnknown;
                        int hr = Marshal.QueryInterface (pItf, ref iid, out iunknown);
                        Marshal.ThrowExceptionForHR (hr);
                }
 
+               internal void Initialize (IntPtr pUnk, ComInteropProxy p)
+               {
+                       proxy = p;
+                       InitializeApartmentDetails ();
+                       iunknown = pUnk;
+               }
+
                internal void Initialize (Type t)
                {
                        InitializeApartmentDetails ();
@@ -101,8 +115,14 @@ namespace System
                        if (iunknown != IntPtr.Zero)
                                return;
 
+                       iunknown = CreateIUnknown (t);
+               }
+
+               internal static IntPtr CreateIUnknown(Type t)
+               {
                        System.Runtime.CompilerServices.RuntimeHelpers.RunClassConstructor (t.TypeHandle);
-                       
+
+                       IntPtr iunknown;
                        ObjectCreationDelegate ocd = ExtensibleClassFactory.GetObjectCreationCallback (t);
                        if (ocd != null) {
                                iunknown = ocd (IntPtr.Zero);
@@ -113,6 +133,8 @@ namespace System
                                int hr = CoCreateInstance (GetCLSID (t), IntPtr.Zero, 0x1 | 0x4 | 0x10, IID_IUnknown, out iunknown);
                                Marshal.ThrowExceptionForHR (hr);
                        }
+
+                       return iunknown;
                }
 
                private void InitializeApartmentDetails ()
index b17cfd62c55c5724bea9f608fbbb058f4382471f..8ef9dcf4680b0a486793b9eb69a4abc518cf75a1 100644 (file)
@@ -230,6 +230,17 @@ public class DirectoryTest
                }\r
        }\r
 \r
+       [Test]\r
+       public void CreateDirectoryRelativePath ()\r
+       {\r
+               var path = Path.Combine (TempFolder, "relativepath", "not_this_folder");\r
+               path = Path.Combine (path, "..");\r
+\r
+               var res = Directory.CreateDirectory (path);\r
+               Assert.AreEqual ("relativepath", res.ToString (), "#1");\r
+               Assert.IsTrue (Directory.Exists (Path.Combine (TempFolder, "relativepath")), "#2");\r
+       }\r
+\r
        [Test]\r
        public void Delete ()\r
        {\r
index 0068c4643b8fdcae08e5070ee5ed340ab9d64cdf..e49a503b566f173e50586f13523d9b9fb8f0c25a 100644 (file)
@@ -141,7 +141,6 @@ namespace MonoTests.System.IO
 
 #if !MOBILE
                [Test]
-               [Category ("NotWorking")]
                public void IsReadOnly ()
                {
                        string path = TempFolder + DSC + "FIT.IsReadOnly.Test";
@@ -755,9 +754,9 @@ namespace MonoTests.System.IO
                                try {
                                        info.MoveTo (destFile);
                                        Assert.Fail ("#1");
-                               } catch (DirectoryNotFoundException ex) {
+                               } catch (FileNotFoundException ex) {
                                        // Could not find a part of the path
-                                       Assert.AreEqual (typeof (DirectoryNotFoundException), ex.GetType (), "#2");
+                                       Assert.AreEqual (typeof (FileNotFoundException), ex.GetType (), "#2");
                                        Assert.IsNull (ex.InnerException, "#3");
                                        Assert.IsNotNull (ex.Message, "#4");
                                }
@@ -880,6 +879,29 @@ namespace MonoTests.System.IO
                        }
                }
 
+               [Test] //Covers #38796
+               public void ToStringAfterMoveTo ()
+               {
+                       string name1 = "FIT.ToStringAfterMoveTo.Test";
+                       string name2 = "FIT.ToStringAfterMoveTo.Test.Alt";
+                       string path1 = TempFolder + DSC + name1;
+                       string path2 = TempFolder + DSC + name2;
+                       DeleteFile (path1);
+                       DeleteFile (path2);
+                       
+                       try {
+                               File.Create (path1).Close ();
+                               FileInfo info = new FileInfo (path1);
+                               Assert.AreEqual (path1, info.ToString (), "#A");
+
+                               info.MoveTo (path2);
+                               Assert.AreEqual (path2, info.ToString (), "#B");
+                       } finally {
+                               DeleteFile (path1);
+                               DeleteFile (path2);
+                       }
+               }
+
 #if !MOBILE
                [Test]
                public void Replace1 ()
index fa37466a77ad7083c62be10b91be468b6d5b5bd9..122e5b65fc24e29f25e4fddb245904208ba8a4cf 100644 (file)
@@ -1586,6 +1586,7 @@ namespace MonoTests.System.Reflection.Emit
                        Assert.IsFalse (arr.IsGenericParameter, "#8");
                        Assert.IsFalse (arr.IsGenericType, "#9");
                        Assert.IsFalse (arr.IsGenericTypeDefinition, "#10");
+                       Assert.IsTrue (arr is TypeInfo, "#11");
                }
 
                [Test]
@@ -1664,6 +1665,7 @@ namespace MonoTests.System.Reflection.Emit
                        Assert.AreEqual ("F[]", arr.Name, "#21");
 
                        Assert.AreEqual (gparam, arr.GetElementType (), "#22");
+                       Assert.IsTrue (arr is TypeInfo, "#23");
                }
 
                [Test]
@@ -1718,6 +1720,7 @@ namespace MonoTests.System.Reflection.Emit
                        Assert.AreEqual ("enum[]", arr.Name, "#21");
 
                        Assert.AreEqual (eb, arr.GetElementType (), "#22");
+                       Assert.IsTrue (arr is TypeInfo, "#23");
                }
 
        }
index 9c566b4bafcc7111e311a308657b7f7c0922191c..900ffec6e7c4e570d6954ebb45176ad648e7912a 100644 (file)
@@ -35,6 +35,7 @@ using System.Diagnostics;
 namespace MonoTests.System.Runtime.ExceptionServices
 {
        [TestFixture]
+       [Category ("BitcodeNotWorking")]
        public class ExceptionDispatchInfoTest
        {
                [Test]
index 11e81774310f6912bbf366272d4a7334cd2db67a..6cdc052f4fb97f8b2d630733e32e5a69a9b814bc 100644 (file)
@@ -39,7 +39,7 @@ namespace MonoTests.System.Security.Cryptography {
                public void Ctor () 
                {
                        var cp = new CspParameters ();
-                       Assert.AreEqual (24, cp.ProviderType);
+                       Assert.AreEqual (1, cp.ProviderType);
                }
        }
 }
index 2ed3b6003c7a440cbfb529a6dbd78b5002aa1ed2..ce1c9793fc57daeef63df5687cbea2c505ac916d 100644 (file)
@@ -103,7 +103,7 @@ namespace MonoTests.System.Threading {
                [Test] // bug #320950
                public void TestDispose2 ()
                {
-                       Timer t = new Timer (o => Callback (o), null, 10, 10);
+                       Timer t = new Timer (o => DoNothing (o), null, 10, 10);
                        t.Dispose ();
                        t.Dispose ();
                }
index 4279cee8ec9d835c8c29d2e4ec86feccb179020b..cbf44c17f358df1b94a0c1977772271af40ac3e4 100644 (file)
@@ -4059,17 +4059,27 @@ namespace MonoTests.System
                        } catch (ArgumentNullException) {}
                }
 
-               void MustAE (string tname) {
+               void MustAE_general (string tname, Func<string,Type> getType) {
                        try {
-                               var res = Type.GetType (tname, name => {
-                                       return Assembly.Load (name);
-                               },(asm,name,ignore) => {
-                                       return (object)asm == null ? Type.GetType (name, false, ignore) : asm.GetType (name, false, ignore);
-                               }, true, false);
+                               var res = getType (tname);
                                Assert.Fail (tname);
                        } catch (ArgumentException) {}
                }
 
+               void MustAE (string typename) {
+                       MustAE_general (typename, tname => {
+                                       return Type.GetType (tname, name => {
+                                                       return Assembly.Load (name);
+                                               },(asm,name,ignore) => {
+                                                       return (object)asm == null ? Type.GetType (name, false, ignore) : asm.GetType (name, false, ignore);
+                                               }, true, false);
+                               });
+               }
+
+               void MustAEnn (string typename) {
+                       MustAE_general (typename, tname => Type.GetType (tname, null, null));
+               }
+
                void MustFNFE (string tname) {
                        try {
                                var res = Type.GetType (tname, name => {
@@ -4152,6 +4162,56 @@ namespace MonoTests.System
                        Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[System.Int32"), null, "#15");
                }
 
+               [Test]
+               public void GetTypeNullDelegatesParseGenericCorrectly () {
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1", null, null), typeof (Foo<>), "#1");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[System.Int32]", null, null), typeof (Foo<int>), "#2");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[[System.Int32]]", null, null), typeof (Foo<int>), "#3");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[System.Int32][]", null, null), typeof (Foo<int>[]), "#4");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[System.Int32][,]", null, null), typeof (Foo<int>[,]), "#5");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[]", null, null), typeof (Foo<>).MakeArrayType(), "#6");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[,]", null, null), typeof (Foo<>).MakeArrayType (2), "#7");
+                       Assert.AreEqual (Type.GetType ("MonoTests.System.Foo`1[][]", null, null), typeof (Foo<>).MakeArrayType ().MakeArrayType (), "#8");
+
+                       MustAEnn ("MonoTests.System.Foo`1[][System.Int32]");
+                       MustAEnn ("MonoTests.System.Foo`1[");
+                       MustAEnn ("MonoTests.System.Foo`1[[");
+                       MustAEnn ("MonoTests.System.Foo`1[[]");
+                       MustAEnn ("MonoTests.System.Foo`1[,");
+                       MustAEnn ("MonoTests.System.Foo`1[*");
+                       MustAEnn ("MonoTests.System.Foo`1[System.Int32");
+               }
+
+               Dictionary<int, T> MakeDictHelper<T> (T[] arr) {
+                       return new Dictionary<int, T>();
+               }
+
+               [Test]
+               public void GetTypeAnonymousParseCorrectly () {
+                       var x = new { X = 1 };
+                       var a = new [] { x };
+                       var d = MakeDictHelper (a);
+
+                       var x_type = x.GetType ();
+                       var a_type = a.GetType ();
+                       var d_type = d.GetType ();
+
+                       Assert.AreEqual (Type.GetType (x_type.ToString ()), x_type, "#1");
+                       Assert.AreEqual (Type.GetType (x_type.ToString (), null, null), x_type, "#2");
+                       Assert.AreEqual (Type.GetType (a_type.ToString ()), a_type, "#3");
+                       Assert.AreEqual (Type.GetType (a_type.ToString (), null, null), a_type, "#4");
+                       Assert.AreEqual (Type.GetType (d_type.ToString ()), d_type, "#5");
+                       Assert.AreEqual (Type.GetType (d_type.ToString (), null, null), d_type, "#6");
+
+                       Assert.AreEqual (Type.GetType (x_type.FullName), x_type, "#7");
+                       Assert.AreEqual (Type.GetType (x_type.FullName, null, null), x_type, "#8");
+                       Assert.AreEqual (Type.GetType (a_type.FullName), a_type, "#9");
+                       Assert.AreEqual (Type.GetType (a_type.FullName, null, null), a_type, "#10");
+                       Assert.AreEqual (Type.GetType (d_type.FullName), d_type, "#11");
+                       Assert.AreEqual (Type.GetType (d_type.FullName, null, null), d_type, "#12");
+
+               }
+
 #if !MONOTOUCH && !MOBILE_STATIC
                [Test]
                [Category ("AndroidNotWorking")] // requires symbol writer
index 35ed33617c26884fa55a28c2d058cfb533a30179..4229e3f8a1070ee43cf9b5aa0bb26bbeb1dbd41c 100644 (file)
@@ -100,7 +100,6 @@ System/DomainManagerInitializationFlags.cs
 System/EmptyArray.cs
 System/Environment.cs
 System/EnvironmentVariableTarget.cs
-System/Exception.cs
 System/GC.cs
 System/GCCollectionMode.cs
 System/GCNotificationStatus.cs
@@ -196,13 +195,11 @@ System.IO/DriveType.cs
 System.IO/File.cs
 System.IO/FileAccess.cs
 System.IO/FileAttributes.cs
-System.IO/FileInfo.cs
 System.IO/FileMode.cs
 System.IO/FileOptions.cs
 System.IO/FileShare.cs
 System.IO/FileStream.cs
 System.IO/FileStreamAsyncResult.cs
-System.IO/FileSystemInfo.cs
 System.IO/HGlobalUnmanagedMemoryStream.cs
 System.IO/LogcatTextWriter.cs
 System.IO/MonoIO.cs
@@ -729,6 +726,7 @@ System.Security.Cryptography/RSAPKCS1SignatureDeformatter.cs
 System.Security.Cryptography/RSAPKCS1SignatureFormatter.cs
 System.Security.Cryptography/SHA1CryptoServiceProvider.cs
 System.Security.Cryptography/TripleDESCryptoServiceProvider.cs
+System.Security.Cryptography.X509Certificates/INativeCertificateHelper.cs
 System.Security.Cryptography.X509Certificates/X509Certificate.cs
 System.Security.Cryptography.X509Certificates/X509Certificate20.cs
 System.Security.Cryptography.X509Certificates/X509CertificateImpl.cs
@@ -972,6 +970,7 @@ ReferenceSources/SecurityContext.cs
 ../../../external/referencesource/mscorlib/system/entrypointnotfoundexception.cs
 ../../../external/referencesource/mscorlib/system/eventargs.cs
 ../../../external/referencesource/mscorlib/system/eventhandler.cs
+../../../external/referencesource/mscorlib/system/exception.cs
 ../../../external/referencesource/mscorlib/system/executionengineexception.cs
 ../../../external/referencesource/mscorlib/system/fieldaccessexception.cs
 ../../../external/referencesource/mscorlib/system/flagsattribute.cs
@@ -999,7 +998,6 @@ ReferenceSources/SecurityContext.cs
 ../../../external/referencesource/mscorlib/system/int64.cs
 ../../../external/referencesource/mscorlib/system/iobservable.cs
 ../../../external/referencesource/mscorlib/system/iobserver.cs
-../../../external/referencesource/mscorlib/system/io/unmanagedmemoryaccessor.cs
 ../../../external/referencesource/mscorlib/system/iprogress.cs
 ../../../external/referencesource/mscorlib/system/iserviceobjectprovider.cs
 ../../../external/referencesource/mscorlib/system/invalidtimezoneexception.cs
@@ -1197,8 +1195,10 @@ ReferenceSources/SecurityContext.cs
 ../../../external/referencesource/mscorlib/system/io/drivenotfoundexception.cs
 ../../../external/referencesource/mscorlib/system/io/endofstreamexception.cs
 ../../../external/referencesource/mscorlib/system/io/ioexception.cs
+../../../external/referencesource/mscorlib/system/io/fileinfo.cs
 ../../../external/referencesource/mscorlib/system/io/fileloadexception.cs
 ../../../external/referencesource/mscorlib/system/io/filenotfoundexception.cs
+../../../external/referencesource/mscorlib/system/io/filesysteminfo.cs
 ../../../external/referencesource/mscorlib/system/io/memorystream.cs
 ../../../external/referencesource/mscorlib/system/io/pathtoolongexception.cs
 ../../../external/referencesource/mscorlib/system/io/pinnedbuffermemorystream.cs
@@ -1209,6 +1209,7 @@ ReferenceSources/SecurityContext.cs
 ../../../external/referencesource/mscorlib/system/io/stringwriter.cs
 ../../../external/referencesource/mscorlib/system/io/textreader.cs
 ../../../external/referencesource/mscorlib/system/io/textwriter.cs
+../../../external/referencesource/mscorlib/system/io/unmanagedmemoryaccessor.cs
 ../../../external/referencesource/mscorlib/system/io/unmanagedmemorystream.cs
 ../../../external/referencesource/mscorlib/system/io/unmanagedmemorystreamwrapper.cs
 
@@ -1257,6 +1258,7 @@ ReferenceSources/SecurityContext.cs
 ../../../external/referencesource/mscorlib/system/reflection/typeinfo.cs
 
 ../../../external/referencesource/mscorlib/system/reflection/emit/methodbuilder.cs
+../../../external/referencesource/mscorlib/system/reflection/emit/symboltype.cs
 
 ../../../external/referencesource/mscorlib/system/resources/__fastresourcecomparer.cs
 ../../../external/referencesource/mscorlib/system/resources/__hresults.cs
diff --git a/mcs/class/corlib/monotouch_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..7287193
--- /dev/null
@@ -0,0 +1,15 @@
+System.Security.Cryptography/MD5CryptoServiceProvider.cs
+System.Security.Cryptography/SHA1CryptoServiceProvider.cs
+System.Security.Cryptography/SHA1CryptoServiceProvider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/descryptoserviceprovider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/rc2cryptoserviceprovider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/rijndaelmanaged.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha1managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha256managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha384managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha512managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/tripledescryptoserviceprovider.cs
+System.Security.Cryptography/RNGCryptoServiceProvider.cs
+../Mono.Security/Mono.Security.Cryptography/ARC4Managed.cs
+../Mono.Security/Mono.Security.Cryptography/MD2Managed.cs
+../Mono.Security/Mono.Security.Cryptography/MD4Managed.cs
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_opt_corlib.dll.sources
deleted file mode 100644 (file)
index be231ef..0000000
+++ /dev/null
@@ -1,4 +0,0 @@
-System/Environment.MonoTouch.opt.cs
-System/Guid.MonoTouch.opt.cs
-System.Text/EncodingHelper.MonoTouch.opt.cs
-System.Security.Cryptography.X509Certificates/X509Helper.MonoTouch.opt.cs
diff --git a/mcs/class/corlib/monotouch_runtime_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_runtime_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..53efeac
--- /dev/null
@@ -0,0 +1 @@
+#include monotouch_corlib.dll.exclude.sources
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_runtime_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_runtime_opt_corlib.dll.sources
deleted file mode 100644 (file)
index d32b506..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_corlib.dll.sources
diff --git a/mcs/class/corlib/monotouch_tv_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_tv_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..53efeac
--- /dev/null
@@ -0,0 +1 @@
+#include monotouch_corlib.dll.exclude.sources
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_tv_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_tv_opt_corlib.dll.sources
deleted file mode 100644 (file)
index d32b506..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_corlib.dll.sources
diff --git a/mcs/class/corlib/monotouch_tv_runtime_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_tv_runtime_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..53efeac
--- /dev/null
@@ -0,0 +1 @@
+#include monotouch_corlib.dll.exclude.sources
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_tv_runtime_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_tv_runtime_opt_corlib.dll.sources
deleted file mode 100644 (file)
index d32b506..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_corlib.dll.sources
diff --git a/mcs/class/corlib/monotouch_watch_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_watch_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..53efeac
--- /dev/null
@@ -0,0 +1 @@
+#include monotouch_corlib.dll.exclude.sources
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_watch_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_watch_opt_corlib.dll.sources
deleted file mode 100644 (file)
index d32b506..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_corlib.dll.sources
diff --git a/mcs/class/corlib/monotouch_watch_runtime_corlib.dll.exclude.sources b/mcs/class/corlib/monotouch_watch_runtime_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..53efeac
--- /dev/null
@@ -0,0 +1 @@
+#include monotouch_corlib.dll.exclude.sources
index da77893bcc50c66f173571e43a57595448b44e27..6acc765c090d0c5e18bf7673c56328dbb30053a8 100644 (file)
@@ -1 +1,15 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/SecRandom.cs
+CommonCrypto/RC4CommonCrypto.cs
+System/Environment.iOS.cs
+System/Guid.MonoTouch.cs
+System/NotSupportedException.iOS.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
+System.Text/EncodingHelper.MonoTouch.cs
diff --git a/mcs/class/corlib/monotouch_watch_runtime_opt_corlib.dll.sources b/mcs/class/corlib/monotouch_watch_runtime_opt_corlib.dll.sources
deleted file mode 100644 (file)
index d32b506..0000000
+++ /dev/null
@@ -1 +0,0 @@
-#include monotouch_opt_corlib.dll.sources
diff --git a/mcs/class/corlib/xammac_corlib.dll.exclude.sources b/mcs/class/corlib/xammac_corlib.dll.exclude.sources
new file mode 100644 (file)
index 0000000..86bb404
--- /dev/null
@@ -0,0 +1,14 @@
+System.Security.Cryptography/MD5CryptoServiceProvider.cs
+System.Security.Cryptography/SHA1CryptoServiceProvider.cs
+System.Security.Cryptography/SHA1CryptoServiceProvider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/descryptoserviceprovider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/rc2cryptoserviceprovider.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/rijndaelmanaged.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha1managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha256managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha384managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/sha512managed.cs
+../../../external/referencesource/mscorlib/system/security/cryptography/tripledescryptoserviceprovider.cs
+../Mono.Security/Mono.Security.Cryptography/ARC4Managed.cs
+../Mono.Security/Mono.Security.Cryptography/MD2Managed.cs
+../Mono.Security/Mono.Security.Cryptography/MD4Managed.cs
index da77893bcc50c66f173571e43a57595448b44e27..f321e0bc800fc1f1ecca58a541972df1fe8b7d29 100644 (file)
@@ -1 +1,10 @@
 #include corlib.dll.sources
+CommonCrypto/CommonCrypto.cs
+CommonCrypto/CryptorTransform.cs
+CommonCrypto/FastCryptorTransform.cs
+CommonCrypto/CorlibExtras.cs
+CommonCrypto/RijndaelManaged.cs
+CommonCrypto/RC4CommonCrypto.cs
+CoreFoundation/CFHelpers.cs
+System.Security.Cryptography.X509Certificates/X509CertificateImplApple.cs
+System.Security.Cryptography.X509Certificates/X509Helper.Apple.cs
diff --git a/mcs/class/corlib/xammac_opt_corlib.dll.sources b/mcs/class/corlib/xammac_opt_corlib.dll.sources
deleted file mode 100644 (file)
index 449e252..0000000
+++ /dev/null
@@ -1 +0,0 @@
-System.Security.Cryptography.X509Certificates/X509Helper.MonoTouch.opt.cs
index 42a1b7aed46b97d1f3a2d3aa829ebd1ca1e69843..316dcc886cdcb804a8eb441fd5f26735fa95d8ef 100644 (file)
@@ -1,35 +1,34 @@
 <html>
 
 <head>
-<title>Microsoft Public License (Ms-PL)</title>
+<title>MIT License</title>
 </head>
 
 <body>
 
 <p><b>This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software.</b></p>
 
-<h2>1. Definitions</h2>
-<p>The terms &#8220;reproduce,&#8221; &#8220;reproduction,&#8221; &#8220;derivative works,&#8221; and &#8220;distribution&#8221; have the same meaning here as under U.S. copyright law.</p>
-<p>A &#8220;contribution&#8221; is the original software, or any additions or changes to the software.</p>
-<p>A &#8220;contributor&#8221; is any person that distributes its contribution under this license.</p>
-<p> &#8220;Licensed patents&#8221; are a contributor&#8217;s patent claims that read directly on its contribution.</p>
-<h2>2. Grant of Rights</h2>
-<p>(A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free copyright 
-license to reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution or any derivative works that you create.</p>
-
-<p>(B) Patent Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, 
-royalty-free license under its licensed patents to make, have made, use, sell, offer for sale, import, and/or otherwise dispose of its contribution in the software or derivative 
-works of the contribution in the software.</p>
-
-<h2>3. Conditions and Limitations</h2><p>(A) No Trademark License- This license does not grant you rights to use any contributors&#8217; name, logo, or trademarks.</p>
-<p>(B) If you bring a patent claim against any contributor over patents that you claim are infringed by the software, your patent license from such contributor to the software ends automatically.</p>
-<p>(C) If you distribute any portion of the software, you must retain all copyright, patent, trademark, and attribution notices that are present in the software.</p>
-<p>(D) If you distribute any portion of the software in source code form, you may do so only under this license by including a complete copy of this license with your distribution. 
-If you distribute any portion of the software in compiled or object code form, you may only do so under a license that complies with this license.</p>
-
-<p>(E) The software is licensed &#8220;as-is.&#8221; You bear the risk of using it. The contributors give no express warranties, guarantees or conditions. You may have additional 
-consumer rights under your local laws which this license cannot change. To the extent permitted under your local laws, the contributors exclude the implied warranties of merchantability, 
-fitness for a particular purpose and non-infringement.</p>
+<pre>
+Permission is hereby granted, free of charge, to any person obtaining
+a copy of this software and associated documentation files (the
+"Software"), to deal in the Software without restriction, including
+without limitation the rights to use, copy, modify, merge, publish,
+distribute, sublicense, and/or sell copies of the Software, and to
+permit persons to whom the Software is furnished to do so, subject to
+the following conditions:
+
+The above copyright notice and this permission notice shall be
+included in all copies or substantial portions of the Software.
+
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+
+</pre>
 
 </body>
 
index b623377bd0e04a8c6d93e9a17150f8e52601ec56..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 100644 (file)
@@ -1,177 +0,0 @@
-{\rtf1\adeflang1025\ansi\ansicpg1252\uc1\adeff31507\deff0\stshfdbch31505\stshfloch31506\stshfhich31506\stshfbi31507\deflang1033\deflangfe1033\themelang1033\themelangfe0\themelangcs0{\fonttbl{\f0\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\f34\fbidi \froman\fcharset1\fprq2{\*\panose 02040503050406030204}Cambria Math;}
-{\flomajor\f31500\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\fdbmajor\f31501\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
-{\fhimajor\f31502\fbidi \froman\fcharset0\fprq2{\*\panose 02040503050406030204}Cambria;}{\fbimajor\f31503\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
-{\flominor\f31504\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\fdbminor\f31505\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}
-{\fhiminor\f31506\fbidi \fswiss\fcharset0\fprq2{\*\panose 020f0502020204030204}Calibri;}{\fbiminor\f31507\fbidi \froman\fcharset0\fprq2{\*\panose 02020603050405020304}Times New Roman;}{\f39\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}
-{\f40\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\f42\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\f43\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\f44\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
-{\f45\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\f46\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\f47\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}
-{\flomajor\f31508\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\flomajor\f31509\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\flomajor\f31511\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}
-{\flomajor\f31512\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\flomajor\f31513\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\flomajor\f31514\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}
-{\flomajor\f31515\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\flomajor\f31516\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\fdbmajor\f31518\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}
-{\fdbmajor\f31519\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\fdbmajor\f31521\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fdbmajor\f31522\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}
-{\fdbmajor\f31523\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\fdbmajor\f31524\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fdbmajor\f31525\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}
-{\fdbmajor\f31526\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\fhimajor\f31528\fbidi \froman\fcharset238\fprq2 Cambria CE;}{\fhimajor\f31529\fbidi \froman\fcharset204\fprq2 Cambria Cyr;}
-{\fhimajor\f31531\fbidi \froman\fcharset161\fprq2 Cambria Greek;}{\fhimajor\f31532\fbidi \froman\fcharset162\fprq2 Cambria Tur;}{\fhimajor\f31535\fbidi \froman\fcharset186\fprq2 Cambria Baltic;}
-{\fbimajor\f31538\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fbimajor\f31539\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\fbimajor\f31541\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}
-{\fbimajor\f31542\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fbimajor\f31543\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\fbimajor\f31544\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}
-{\fbimajor\f31545\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fbimajor\f31546\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\flominor\f31548\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}
-{\flominor\f31549\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}{\flominor\f31551\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\flominor\f31552\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}
-{\flominor\f31553\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}{\flominor\f31554\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\flominor\f31555\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}
-{\flominor\f31556\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}{\fdbminor\f31558\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fdbminor\f31559\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
-{\fdbminor\f31561\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fdbminor\f31562\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fdbminor\f31563\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
-{\fdbminor\f31564\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fdbminor\f31565\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fdbminor\f31566\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}
-{\fhiminor\f31568\fbidi \fswiss\fcharset238\fprq2 Calibri CE;}{\fhiminor\f31569\fbidi \fswiss\fcharset204\fprq2 Calibri Cyr;}{\fhiminor\f31571\fbidi \fswiss\fcharset161\fprq2 Calibri Greek;}{\fhiminor\f31572\fbidi \fswiss\fcharset162\fprq2 Calibri Tur;}
-{\fhiminor\f31575\fbidi \fswiss\fcharset186\fprq2 Calibri Baltic;}{\fbiminor\f31578\fbidi \froman\fcharset238\fprq2 Times New Roman CE;}{\fbiminor\f31579\fbidi \froman\fcharset204\fprq2 Times New Roman Cyr;}
-{\fbiminor\f31581\fbidi \froman\fcharset161\fprq2 Times New Roman Greek;}{\fbiminor\f31582\fbidi \froman\fcharset162\fprq2 Times New Roman Tur;}{\fbiminor\f31583\fbidi \froman\fcharset177\fprq2 Times New Roman (Hebrew);}
-{\fbiminor\f31584\fbidi \froman\fcharset178\fprq2 Times New Roman (Arabic);}{\fbiminor\f31585\fbidi \froman\fcharset186\fprq2 Times New Roman Baltic;}{\fbiminor\f31586\fbidi \froman\fcharset163\fprq2 Times New Roman (Vietnamese);}}
-{\colortbl;\red0\green0\blue0;\red0\green0\blue255;\red0\green255\blue255;\red0\green255\blue0;\red255\green0\blue255;\red255\green0\blue0;\red255\green255\blue0;\red255\green255\blue255;\red0\green0\blue128;\red0\green128\blue128;\red0\green128\blue0;
-\red128\green0\blue128;\red128\green0\blue0;\red128\green128\blue0;\red128\green128\blue128;\red192\green192\blue192;}{\*\defchp \fs22\loch\af31506\hich\af31506\dbch\af31505 }{\*\defpap \ql \li0\ri0\sa200\sl276\slmult1
-\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 }\noqfpromote {\stylesheet{\ql \li0\ri0\sa200\sl276\slmult1\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025 
-\ltrch\fcs0 \fs22\lang1033\langfe1033\loch\f31506\hich\af31506\dbch\af31505\cgrid\langnp1033\langfenp1033 \snext0 \sqformat \spriority0 Normal;}{\*\cs10 \additive \ssemihidden \sunhideused \spriority1 Default Paragraph Font;}{\*
-\ts11\tsrowd\trftsWidthB3\trpaddl108\trpaddr108\trpaddfl3\trpaddft3\trpaddfb3\trpaddfr3\trcbpat1\trcfpat1\tblind0\tblindtype3\tscellwidthfts0\tsvertalt\tsbrdrt\tsbrdrl\tsbrdrb\tsbrdrr\tsbrdrdgl\tsbrdrdgr\tsbrdrh\tsbrdrv \ql \li0\ri0\sa200\sl276\slmult1
-\widctlpar\wrapdefault\aspalpha\aspnum\faauto\adjustright\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025 \ltrch\fcs0 \fs22\lang1033\langfe1033\loch\f31506\hich\af31506\dbch\af31505\cgrid\langnp1033\langfenp1033 
-\snext11 \ssemihidden \sunhideused \sqformat Normal Table;}}{\*\rsidtbl \rsid11612883}{\mmathPr\mmathFont34\mbrkBin0\mbrkBinSub0\msmallFrac0\mdispDef1\mlMargin0\mrMargin0\mdefJc1\mwrapIndent1440\mintLim0\mnaryLim1}{\info{\author dinov}{\operator dinov}
-{\creatim\yr2007\mo10\dy30\hr14\min43}{\revtim\yr2007\mo10\dy30\hr14\min43}{\version2}{\edmins1}{\nofpages2}{\nofwords404}{\nofchars2212}{\*\company Microsoft}{\nofcharsws2611}{\vern32893}}{\*\xmlnstbl {\xmlns1 http://schemas.microsoft.com/office/word/200
-3/wordml}}\paperw12240\paperh15840\margl1440\margr1440\margt1440\margb1440\gutter0\ltrsect 
-\widowctrl\ftnbj\aenddoc\trackmoves1\trackformatting1\donotembedsysfont0\relyonvml0\donotembedlingdata1\grfdocevents0\validatexml0\showplaceholdtext0\ignoremixedcontent0\saveinvalidxml0\showxmlerrors0\horzdoc\dghspace120\dgvspace120\dghorigin1701
-\dgvorigin1984\dghshow0\dgvshow3\jcompress\viewkind1\viewscale100\rsidroot11612883 \fet0{\*\wgrffmtfilter 2450}\ilfomacatclnup0\ltrpar \sectd \ltrsect\linex0\sectdefaultcl\sftnbj {\*\pnseclvl1\pnucrm\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl2
-\pnucltr\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl3\pndec\pnstart1\pnindent720\pnhang {\pntxta .}}{\*\pnseclvl4\pnlcltr\pnstart1\pnindent720\pnhang {\pntxta )}}{\*\pnseclvl5\pndec\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl6
-\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl7\pnlcrm\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl8\pnlcltr\pnstart1\pnindent720\pnhang {\pntxtb (}{\pntxta )}}{\*\pnseclvl9\pnlcrm\pnstart1\pnindent720\pnhang 
-{\pntxtb (}{\pntxta )}}\pard\plain \ltrpar\ql \li0\ri0\sb100\sa100\nowidctlpar\wrapdefault\faauto\rin0\lin0\itap0 \rtlch\fcs1 \af31507\afs22\alang1025 \ltrch\fcs0 
-\fs22\lang1033\langfe1033\loch\af31506\hich\af31506\dbch\af31505\cgrid\langnp1033\langfenp1033 {\rtlch\fcs1 \ab\af0\afs28 \ltrch\fcs0 \b\f0\fs28\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 Microsoft }{\rtlch\fcs1 \ab\af0\afs28 \ltrch\fcs0 
-\b\f0\fs28\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 Public }{\rtlch\fcs1 \ab\af0\afs28 \ltrch\fcs0 \b\f0\fs28\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 License (Ms-PL)
-\par }{\rtlch\fcs1 \ab\af0\afs24 \ltrch\fcs0 \b\f0\fs24\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 
-This license governs use of the accompanying software. If you use the software, you accept this license. If you do not accept the license, do not use the software.}{\rtlch\fcs1 \af0\afs24 \ltrch\fcs0 \f0\fs24\insrsid11612883 
-\par }{\rtlch\fcs1 \ab\af0\afs36 \ltrch\fcs0 \b\f0\fs36\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 1. Definitions
-\par }{\rtlch\fcs1 \af0\afs24 \ltrch\fcs0 \f0\fs24\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 \hich\f0 The terms \'93\loch\f0 \hich\f0 reproduce,\'94\loch\f0 \hich\f0  \'93\loch\f0 \hich\f0 reproduction,\'94\loch\f0 \hich\f0  \'93
-\hich\af0\dbch\af31505\loch\f0 \hich\f0 derivative works,\'94\loch\f0 \hich\f0  and \'93\loch\f0 \hich\f0 distribution\'94\loch\f0  have the same meaning here as under U.S. copyright law.
-\par \hich\af0\dbch\af31505\loch\f0 \hich\f0 A \'93\loch\f0 \hich\f0 contribution\'94\loch\f0  is the original software, or any additions or changes to the software.
-\par \hich\af0\dbch\af31505\loch\f0 \hich\f0 A \'93\loch\f0 \hich\f0 contributor\'94\loch\f0  is any person that distributes its contribution under this\hich\af0\dbch\af31505\loch\f0  license.
-\par \loch\af0\dbch\af31505\hich\f0 \'93\loch\f0 \hich\f0 Licensed patents\'94\loch\f0  are a contributor\hich\f0 \rquote \loch\f0 s patent claims that read directly on its contribution.
-\par }{\rtlch\fcs1 \ab\af0\afs36 \ltrch\fcs0 \b\f0\fs36\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 2. Grant of Rights
-\par }{\rtlch\fcs1 \af0\afs24 \ltrch\fcs0 \f0\fs24\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 (A) Copyright Grant- Subject to the terms of this license, including the license conditions and limitations in section 3, each contrib
-\hich\af0\dbch\af31505\loch\f0 utor grants you a non-exclusive, worldwide, royalty-free copyright license to reproduce its contribution, prepare derivative works of its contribution, and distribute its contribution or any derivative works that you create.
-
-\par \hich\af0\dbch\af31505\loch\f0 (B) Patent Grant- Subject to th\hich\af0\dbch\af31505\loch\f0 
-e terms of this license, including the license conditions and limitations in section 3, each contributor grants you a non-exclusive, worldwide, royalty-free license under its licensed patents to make, have made, use, sell, offer for sale, import, and/or o
-\hich\af0\dbch\af31505\loch\f0 t\hich\af0\dbch\af31505\loch\f0 herwise dispose of its contribution in the software or derivative works of the contribution in the software.
-\par }{\rtlch\fcs1 \ab\af0\afs36 \ltrch\fcs0 \b\f0\fs36\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 3. Conditions and Limitations
-\par }{\rtlch\fcs1 \af0\afs24 \ltrch\fcs0 \f0\fs24\insrsid11612883 \hich\af0\dbch\af31505\loch\f0 (A) No Trademark License- This license does not grant you rights to use any contributors\hich\f0 \rquote \loch\f0  name, logo, or trademarks.
-\par \hich\af0\dbch\af31505\loch\f0 (B) If you bring a patent claim against any contributor over patents that you claim are infringed by the software, your patent license from such contributor to the software ends automatically.
-\par \hich\af0\dbch\af31505\loch\f0 (C) If you distribute any portion of the software, you must ret\hich\af0\dbch\af31505\loch\f0 ain all copyright, patent, trademark, and attribution notices that are present in the software.
-\par \hich\af0\dbch\af31505\loch\f0 (D) If you distribute any portion of the software in source code form, you may do so only under this license by including a complete copy of this license with y\hich\af0\dbch\af31505\loch\f0 
-our distribution. If you distribute any portion of the software in compiled or object code form, you may only do so under a license that complies with this license.
-\par \hich\af0\dbch\af31505\loch\f0 \hich\f0 (E) The software is licensed \'93\loch\f0 \hich\f0 as-is.\'94\loch\f0  You bear the risk of using it. The contributors give \hich\af0\dbch\af31505\loch\f0 
-no express warranties, guarantees or conditions. You may have additional consumer rights under your local laws which this license cannot change. To the extent permitted under your local laws, the contributors exclude the implied warranties of merchantabil
-\hich\af0\dbch\af31505\loch\f0 i\hich\af0\dbch\af31505\loch\f0 ty, fitness for a particular purpose and non-infringement.
-\par }\pard \ltrpar\ql \li0\ri0\nowidctlpar\wrapdefault\faauto\rin0\lin0\itap0 {\rtlch\fcs1 \af0\afs24 \ltrch\fcs0 \f0\fs24\insrsid11612883 
-\par }{\*\themedata 504b030414000600080000002100828abc13fa0000001c020000130000005b436f6e74656e745f54797065735d2e786d6cac91cb6ac3301045f785fe83d0b6d8
-72ba28a5d8cea249777d2cd20f18e4b12d6a8f843409c9df77ecb850ba082d74231062ce997b55ae8fe3a00e1893f354e9555e6885647de3a8abf4fbee29bbd7
-2a3150038327acf409935ed7d757e5ee14302999a654e99e393c18936c8f23a4dc072479697d1c81e51a3b13c07e4087e6b628ee8cf5c4489cf1c4d075f92a0b
-44d7a07a83c82f308ac7b0a0f0fbf90c2480980b58abc733615aa2d210c2e02cb04430076a7ee833dfb6ce62e3ed7e14693e8317d8cd0433bf5c60f53fea2fe7
-065bd80facb647e9e25c7fc421fd2ddb526b2e9373fed4bb902e182e97b7b461e6bfad3f010000ffff0300504b030414000600080000002100a5d6a7e7c00000
-00360100000b0000005f72656c732f2e72656c73848fcf6ac3300c87ef85bd83d17d51d2c31825762fa590432fa37d00e1287f68221bdb1bebdb4fc7060abb08
-84a4eff7a93dfeae8bf9e194e720169aaa06c3e2433fcb68e1763dbf7f82c985a4a725085b787086a37bdbb55fbc50d1a33ccd311ba548b63095120f88d94fbc
-52ae4264d1c910d24a45db3462247fa791715fd71f989e19e0364cd3f51652d73760ae8fa8c9ffb3c330cc9e4fc17faf2ce545046e37944c69e462a1a82fe353
-bd90a865aad41ed0b5b8f9d6fd010000ffff0300504b0304140006000800000021006b799616830000008a0000001c0000007468656d652f7468656d652f7468
-656d654d616e616765722e786d6c0ccc4d0ac3201040e17da17790d93763bb284562b2cbaebbf600439c1a41c7a0d29fdbd7e5e38337cedf14d59b4b0d592c9c
-070d8a65cd2e88b7f07c2ca71ba8da481cc52c6ce1c715e6e97818c9b48d13df49c873517d23d59085adb5dd20d6b52bd521ef2cdd5eb9246a3d8b4757e8d3f7
-29e245eb2b260a0238fd010000ffff0300504b03041400060008000000210096b5ade296060000501b0000160000007468656d652f7468656d652f7468656d65
-312e786d6cec594f6fdb3614bf0fd87720746f6327761a07758ad8b19b2d4d1bc46e871e698996d850a240d2497d1bdae38001c3ba618715d86d87615b8116d8
-a5fb34d93a6c1dd0afb0475292c5585e9236d88aad3e2412f9e3fbff1e1fa9abd7eec70c1d1221294fda5efd72cd4324f1794093b0eddd1ef62fad79482a9c04
-98f184b4bd2991deb58df7dfbb8ad755446282607d22d771db8b944ad79796a40fc3585ee62949606ecc458c15bc8a702910f808e8c66c69b9565b5d8a314d3c
-94e018c8de1a8fa94fd05093f43672e23d06af89927ac06762a049136785c10607758d9053d965021d62d6f6804fc08f86e4bef210c352c144dbab999fb7b471
-7509af678b985ab0b6b4ae6f7ed9ba6c4170b06c788a705430adf71bad2b5b057d03606a1ed7ebf5babd7a41cf00b0ef83a6569632cd467faddec9699640f671
-9e76b7d6ac355c7c89feca9cccad4ea7d36c65b258a206641f1b73f8b5da6a6373d9c11b90c537e7f08dce66b7bbeae00dc8e257e7f0fd2badd5868b37a088d1
-e4600ead1ddaef67d40bc898b3ed4af81ac0d76a197c86826828a24bb318f3442d8ab518dfe3a20f000d6458d104a9694ac6d88728eee2782428d60cf03ac1a5
-193be4cbb921cd0b495fd054b5bd0f530c1931a3f7eaf9f7af9e3f45c70f9e1d3ff8e9f8e1c3e3073f5a42ceaa6d9c84e5552fbffdeccfc71fa33f9e7ef3f2d1
-17d57859c6fffac327bffcfc793510d26726ce8b2f9ffcf6ecc98baf3efdfdbb4715f04d814765f890c644a29be408edf3181433567125272371be15c308d3f2
-8acd249438c19a4b05fd9e8a1cf4cd296699771c393ac4b5e01d01e5a30a787d72cf1178108989a2159c77a2d801ee72ce3a5c545a6147f32a99793849c26ae6
-6252c6ed637c58c5bb8b13c7bfbd490a75330f4b47f16e441c31f7184e140e494214d273fc80900aedee52ead87597fa824b3e56e82e451d4c2b4d32a423279a
-668bb6690c7e9956e90cfe766cb37b077538abd27a8b1cba48c80acc2a841f12e698f13a9e281c57911ce298950d7e03aba84ac8c154f8655c4f2af074481847
-bd804859b5e696007d4b4edfc150b12addbecba6b18b148a1e54d1bc81392f23b7f84137c2715a851dd0242a633f900710a218ed715505dfe56e86e877f0034e
-16bafb0e258ebb4faf06b769e888340b103d3311da9750aa9d0a1cd3e4efca31a3508f6d0c5c5c398602f8e2ebc71591f5b616e24dd893aa3261fb44f95d843b
-5974bb5c04f4edafb95b7892ec1108f3f98de75dc97d5772bdff7cc95d94cf672db4b3da0a6557f70db629362d72bcb0431e53c6066acac80d699a6409fb44d0
-8741bdce9c0e4971624a2378cceaba830b05366b90e0ea23aaa241845368b0eb9e2612ca8c742851ca251ceccc70256d8d87265dd96361531f186c3d9058edf2
-c00eafe8e1fc5c509031bb4d680e9f39a3154de0accc56ae644441edd76156d7429d995bdd88664a9dc3ad50197c38af1a0c16d684060441db02565e85f3b966
-0d0713cc48a0ed6ef7dedc2dc60b17e92219e180643ed27acffba86e9c94c78ab90980d8a9f0913ee49d62b512b79626fb06dccee2a432bbc60276b9f7dec44b
-7904cfbca4f3f6443ab2a49c9c2c41476dafd55c6e7ac8c769db1bc399161ee314bc2e75cf8759081743be1236ec4f4d6693e5336fb672c5dc24a8c33585b5fb
-9cc24e1d4885545b58463634cc5416022cd19cacfccb4d30eb45296023fd35a458598360f8d7a4003bbaae25e331f155d9d9a5116d3bfb9a95523e51440ca2e0
-088dd844ec6370bf0e55d027a012ae264c45d02f708fa6ad6da6dce29c255df9f6cae0ec38666984b372ab5334cf640b37795cc860de4ae2816e95b21be5ceaf
-8a49f90b52a51cc6ff3355f47e0237052b81f6800fd7b802239daf6d8f0b1571a8426944fdbe80c6c1d40e8816b88b8569082ab84c36ff0539d4ff6dce591a26
-ade1c0a7f669880485fd484582903d284b26fa4e2156cff62e4b9265844c4495c495a9157b440e091bea1ab8aaf7760f4510eaa69a6465c0e04ec69ffb9e65d0
-28d44d4e39df9c1a52ecbd3607fee9cec7263328e5d661d3d0e4f62f44acd855ed7ab33cdf7bcb8ae889599bd5c8b3029895b6825696f6af29c239b75a5bb1e6
-345e6ee6c28117e73586c1a2214ae1be07e93fb0ff51e133fb65426fa843be0fb515c187064d0cc206a2fa926d3c902e907670048d931db4c1a44959d366ad93
-b65abe595f70a75bf03d616c2dd959fc7d4e6317cd99cbcec9c58b34766661c7d6766ca1a9c1b327531486c6f941c638c67cd22a7f75e2a37be0e82db8df9f30
-254d30c1372581a1f51c983c80e4b71ccdd28dbf000000ffff0300504b0304140006000800000021000dd1909fb60000001b010000270000007468656d652f74
-68656d652f5f72656c732f7468656d654d616e616765722e786d6c2e72656c73848f4d0ac2301484f78277086f6fd3ba109126dd88d0add40384e4350d363f24
-51eced0dae2c082e8761be9969bb979dc9136332de3168aa1a083ae995719ac16db8ec8e4052164e89d93b64b060828e6f37ed1567914b284d262452282e3198
-720e274a939cd08a54f980ae38a38f56e422a3a641c8bbd048f7757da0f19b017cc524bd62107bd5001996509affb3fd381a89672f1f165dfe514173d9850528
-a2c6cce0239baa4c04ca5bbabac4df000000ffff0300504b01022d0014000600080000002100828abc13fa0000001c0200001300000000000000000000000000
-000000005b436f6e74656e745f54797065735d2e786d6c504b01022d0014000600080000002100a5d6a7e7c0000000360100000b000000000000000000000000
-002b0100005f72656c732f2e72656c73504b01022d00140006000800000021006b799616830000008a0000001c00000000000000000000000000140200007468
-656d652f7468656d652f7468656d654d616e616765722e786d6c504b01022d001400060008000000210096b5ade296060000501b000016000000000000000000
-00000000d10200007468656d652f7468656d652f7468656d65312e786d6c504b01022d00140006000800000021000dd1909fb60000001b010000270000000000
-00000000000000009b0900007468656d652f7468656d652f5f72656c732f7468656d654d616e616765722e786d6c2e72656c73504b050600000000050005005d010000960a00000000}
-{\*\colorschememapping 3c3f786d6c2076657273696f6e3d22312e302220656e636f64696e673d225554462d3822207374616e64616c6f6e653d22796573223f3e0d0a3c613a636c724d
-617020786d6c6e733a613d22687474703a2f2f736368656d61732e6f70656e786d6c666f726d6174732e6f72672f64726177696e676d6c2f323030362f6d6169
-6e22206267313d226c743122207478313d22646b3122206267323d226c743222207478323d22646b322220616363656e74313d22616363656e74312220616363
-656e74323d22616363656e74322220616363656e74333d22616363656e74332220616363656e74343d22616363656e74342220616363656e74353d22616363656e74352220616363656e74363d22616363656e74362220686c696e6b3d22686c696e6b2220666f6c486c696e6b3d22666f6c486c696e6b222f3e}
-{\*\latentstyles\lsdstimax267\lsdlockeddef0\lsdsemihiddendef1\lsdunhideuseddef1\lsdqformatdef0\lsdprioritydef99{\lsdlockedexcept \lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority0 \lsdlocked0 Normal;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority9 \lsdlocked0 heading 1;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 2;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 3;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 4;
-\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 5;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 6;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 7;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 8;\lsdqformat1 \lsdpriority9 \lsdlocked0 heading 9;
-\lsdpriority39 \lsdlocked0 toc 1;\lsdpriority39 \lsdlocked0 toc 2;\lsdpriority39 \lsdlocked0 toc 3;\lsdpriority39 \lsdlocked0 toc 4;\lsdpriority39 \lsdlocked0 toc 5;\lsdpriority39 \lsdlocked0 toc 6;\lsdpriority39 \lsdlocked0 toc 7;
-\lsdpriority39 \lsdlocked0 toc 8;\lsdpriority39 \lsdlocked0 toc 9;\lsdqformat1 \lsdpriority35 \lsdlocked0 caption;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority10 \lsdlocked0 Title;\lsdpriority1 \lsdlocked0 Default Paragraph Font;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority11 \lsdlocked0 Subtitle;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority22 \lsdlocked0 Strong;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority20 \lsdlocked0 Emphasis;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority59 \lsdlocked0 Table Grid;\lsdunhideused0 \lsdlocked0 Placeholder Text;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority1 \lsdlocked0 No Spacing;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading;\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List;\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List;\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List;\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid;\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 1;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 1;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 1;\lsdunhideused0 \lsdlocked0 Revision;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority34 \lsdlocked0 List Paragraph;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority29 \lsdlocked0 Quote;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority30 \lsdlocked0 Intense Quote;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 1;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 1;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 1;\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 2;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 2;\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 3;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 3;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 3;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 3;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 3;\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 3;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 4;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 4;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 4;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 4;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 4;\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 5;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 5;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 5;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 5;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 5;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 5;\lsdsemihidden0 \lsdunhideused0 \lsdpriority60 \lsdlocked0 Light Shading Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority61 \lsdlocked0 Light List Accent 6;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority62 \lsdlocked0 Light Grid Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority63 \lsdlocked0 Medium Shading 1 Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority64 \lsdlocked0 Medium Shading 2 Accent 6;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority65 \lsdlocked0 Medium List 1 Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority66 \lsdlocked0 Medium List 2 Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority67 \lsdlocked0 Medium Grid 1 Accent 6;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority68 \lsdlocked0 Medium Grid 2 Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority69 \lsdlocked0 Medium Grid 3 Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority70 \lsdlocked0 Dark List Accent 6;
-\lsdsemihidden0 \lsdunhideused0 \lsdpriority71 \lsdlocked0 Colorful Shading Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority72 \lsdlocked0 Colorful List Accent 6;\lsdsemihidden0 \lsdunhideused0 \lsdpriority73 \lsdlocked0 Colorful Grid Accent 6;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority19 \lsdlocked0 Subtle Emphasis;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority21 \lsdlocked0 Intense Emphasis;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority31 \lsdlocked0 Subtle Reference;\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority32 \lsdlocked0 Intense Reference;
-\lsdsemihidden0 \lsdunhideused0 \lsdqformat1 \lsdpriority33 \lsdlocked0 Book Title;\lsdpriority37 \lsdlocked0 Bibliography;\lsdqformat1 \lsdpriority39 \lsdlocked0 TOC Heading;}}{\*\datastore 010500000200000018000000
-4d73786d6c322e534158584d4c5265616465722e352e3000000000000000000000060000
-d0cf11e0a1b11ae1000000000000000000000000000000003e000300feff090006000000000000000000000001000000010000000000000000100000feffffff00000000feffffff0000000000000000ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-fffffffffffffffffdfffffffeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff
-ffffffffffffffffffffffffffffffff52006f006f007400200045006e00740072007900000000000000000000000000000000000000000000000000000000000000000000000000000000000000000016000500ffffffffffffffffffffffffec69d9888b8b3d4c859eaf6cd158be0f0000000000000000000000009055
-58f93d1bc801feffffff00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff00000000000000000000000000000000000000000000000000000000
-00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff0000000000000000000000000000000000000000000000000000
-000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000ffffffffffffffffffffffff000000000000000000000000000000000000000000000000
-0000000000000000000000000000000000000000000000000105000000000000}}
\ No newline at end of file
index 1c85d9abac643e6f5038fa7815a51c2eac5d7da7..50f84cfd617c820f399f74f922a2aec939654b99 100644 (file)
@@ -111,11 +111,12 @@ LIB_MCS_FLAGS = \
        /resource:Resources/mono-ecma.xsl,mono-ecma.xsl                   \
        /resource:Resources/toc-html.xsl,toc-html.xsl                     \
        $(IMAGE_RESOURCE_COMMAND)                                                             \
-       /r:$(corlib)
+       /publicsign
 
 CLEAN_FILES += $(the_lib).config
 
-TEST_MCS_FLAGS = /r:System.dll /r:System.Core.dll /r:System.Xml.dll
+TEST_MCS_FLAGS =
+TEST_LIB_REFS = System System.Core System.Xml
 
 DOC_SOURCE_DIRS = \
        ../../docs \
index f30dae6f26941cec62d8d36d15dfb1bd1227974b..2c37329cd15342b852201f9c230bd5f42a01b3b6 100644 (file)
@@ -83,6 +83,36 @@ dist-local: dist-default
 
 csproj-local install-local uninstall-local:
 
+CS0029-26-lib.dll : CS0029-26-lib.cs
+       $(CSCOMPILE) /target:library /publicsign /out:$@ $<
+
+CS0266-25-lib.dll: CS0266-25-lib.cs
+       $(CSCOMPILE) /target:library /r:$(topdir)/class/lib/$(PROFILE)/System.Core.dll /out:$@ $<
+
+dlls/first/CS1701-lib.dll: dlls/first/CS1701-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/first/CS1702-lib.dll: dlls/first/CS1702-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/first/CS1703-lib.dll: dlls/first/CS1703-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/first/CS1705-lib.dll: dlls/first/CS1705-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/second/CS1701-lib.dll: dlls/second/CS1701-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/second/CS1702-lib.dll: dlls/second/CS1702-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/second/CS1703-lib.dll: dlls/second/CS1703-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
+dlls/second/CS1705-lib.dll: dlls/second/CS1705-lib.cs
+       $(CSCOMPILE) /target:library /warn:0 /publicsign /out:$@ $<
+
 CS1701-lib.dll : CS1701-lib.cs
        $(CSCOMPILE) /target:library /warn:0 /r:dlls/first/CS1701-lib.dll /out:$@ $<
 
diff --git a/mcs/errors/cs0023-27.cs b/mcs/errors/cs0023-27.cs
new file mode 100644 (file)
index 0000000..068c08a
--- /dev/null
@@ -0,0 +1,13 @@
+// CS0023: The `?' operator cannot be applied to operand of type `T'
+// Line: 11
+
+class C2<T>
+{
+       C2<T> i;
+       T field;
+
+       public void Foo ()
+       {
+               var x = i?.field;
+       }
+}
\ No newline at end of file
diff --git a/mcs/errors/cs0023-28.cs b/mcs/errors/cs0023-28.cs
new file mode 100644 (file)
index 0000000..e9f7942
--- /dev/null
@@ -0,0 +1,15 @@
+// CS0023: The `?' operator cannot be applied to operand of type `T'
+// Line: 13
+
+interface IFoo<T>
+{
+       T Call ();
+}
+
+class C1
+{
+       U Foo<T, U> (IFoo<T> t)
+       {
+               return t?.Call ();
+       }
+}
diff --git a/mcs/errors/cs0023-29.cs b/mcs/errors/cs0023-29.cs
new file mode 100644 (file)
index 0000000..aea3068
--- /dev/null
@@ -0,0 +1,10 @@
+// CS0023: The `?' operator cannot be applied to operand of type `T'
+// Line: 8
+
+class X
+{
+       static void Bug<T>(System.Func<T> func)
+       {
+               var r = func?.Invoke ();
+       }
+}
\ No newline at end of file
index 723b603c5f26ed85bd85dcfc73f9826ccc440817..9fb47abf6d486d9ba4d78811a9d0e68f420f3d13 100644 (file)
@@ -1,4 +1,4 @@
-// CS0029: Cannot implicitly convert type `B [cs0029-26, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null]' to `B [CS0029-26-lib, Version=1.0.0.0, Culture=neutral, PublicKeyToken=36f3ae7e947792e3]'
+// CS0029: Cannot implicitly convert type `B [cs0029-26, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null -- *PATH*/cs0029-26.cs]' to `B [CS0029-26-lib, Version=1.0.0.0, Culture=neutral, PublicKeyToken=36f3ae7e947792e3 -- *PATH*/CS0029-26-lib.dll]'
 // Line: 16
 // Compiler options: -r:R1=CS0029-26-lib.dll
 
diff --git a/mcs/errors/cs0266-30.cs b/mcs/errors/cs0266-30.cs
new file mode 100644 (file)
index 0000000..62cc53f
--- /dev/null
@@ -0,0 +1,14 @@
+// CS0266: Cannot implicitly convert type `Foo<int>.FooEvent' to `Foo<string>.FooEvent'. An explicit conversion exists (are you missing a cast?)
+// Line: 12
+
+class Foo<T> {
+       public event FooEvent Event;
+       public delegate T FooEvent();
+}
+
+class CompilerCrashTest {
+       static void Main() {
+               Foo<string> foo = new Foo<string>();
+               foo.Event += new Foo<int>.FooEvent (() => 0);
+       }
+}
index 3a3e789e0b0c9bcb29064ed565ec931016c75dac..01285712a2b3787590464510bc71d67f99167ed0 100644 (file)
@@ -12,19 +12,21 @@ EXTRA_DISTFILES = \
        cs-parser.jay           \
        mcs.exe.sources
 
-LIB_REFS = System System.Core System.Xml
-
 ifeq (basic, $(PROFILE))
+LOCAL_MCS_FLAGS += -r:System.dll -r:System.Core.dll -r:System.Xml.dll -debug
+
 PROGRAM = basic.exe
 sourcefile = mcs.exe.sources
 else
+LIB_REFS = System System.Core System.Xml
+
 PROGRAM_USE_INTERMEDIATE_FILE = true
 PROGRAM = mcs.exe
 the_libdir = $(topdir)/class/lib/build/
-LOCAL_MCS_FLAGS += -lib:$(topdir)/class/lib/build -debug
+LOCAL_MCS_FLAGS += -debug
 endif
 
-LOCAL_MCS_FLAGS += -d:STATIC,NO_SYMBOL_WRITER,NO_AUTHENTICODE -r:System.Core.dll -r:System.Xml.dll
+LOCAL_MCS_FLAGS += -d:STATIC,NO_SYMBOL_WRITER,NO_AUTHENTICODE
 
 ifndef NO_THREAD_ABORT
 REFERENCE_SOURCES_FLAGS += -d:MONO_FEATURE_THREAD_ABORT
index edc538e7d2ed66a09ab7b5cbd397aec15b3ac3d0..bcf7ddffa21cd928e8b8a6cbfb811c2735940f7f 100644 (file)
@@ -940,7 +940,8 @@ namespace Mono.CSharp
 
                TypeParameterSpec[] ITypeDefinition.TypeParameters {
                        get {
-                               return PartialContainer.CurrentTypeParameters.Types;
+                               var ctp = PartialContainer.CurrentTypeParameters;
+                               return ctp == null ? TypeParameterSpec.EmptyTypes : ctp.Types;
                        }
                }
 
index 1dfb747ba6a46f96ebff889b48259408c371f46a..d5ba75c12813af9d07e4b3182134f82cc3e557f9 100644 (file)
@@ -1263,10 +1263,15 @@ namespace Mono.CSharp
 
                        if (conditionalAccess) {
                                if (!ec.ConditionalAccess.Statement) {
-                                       if (ec.ConditionalAccess.Type.IsNullableType)
-                                               Nullable.LiftedNull.Create (ec.ConditionalAccess.Type, Location.Null).Emit (ec);
-                                       else
+                                       var t = ec.ConditionalAccess.Type;
+                                       if (t.IsNullableType)
+                                               Nullable.LiftedNull.Create (t, Location.Null).Emit (ec);
+                                       else {
                                                ec.EmitNull ();
+
+                                               if (t.IsGenericParameter)
+                                                       ec.Emit (OpCodes.Unbox_Any, t);
+                                       }
                                }
 
                                ec.Emit (OpCodes.Br, ec.ConditionalAccess.EndLabel);
index 68477b3c1ed34bf07220b57999433d23dfc004a4..a0ae78cdf518e42737b571c830e08a99adf00747 100644 (file)
@@ -2245,7 +2245,7 @@ namespace Mono.CSharp {
                                return IsLeftResolvedExpressionValid (dmb.Arguments [0].Expr);
                        }
 
-                       if (expr is ConstantExpr || expr is TypeExpr || expr is NamespaceExpression || expr is This)
+                       if (expr is ConstantExpr || expr is TypeExpr || expr is NamespaceExpression || expr is VariableReference)
                                return true;
 
                        return false;
index 7b5ffadf328884fdeaf5bc532468b005be5f98f2..b2399c8bd89d45c71aee3882c56bb09c8fddd2e1 100644 (file)
@@ -116,6 +116,8 @@ namespace Mono.CSharp
 
                public ExceptionStatement CurrentTryBlock { get; set; }
 
+               public TryCatch CurrentTryCatch { get; set; }
+
                public LoopStatement EnclosingLoop { get; set; }
 
                public LoopStatement EnclosingLoopOrSwitch { get; set; }
index b0c771f7207b2eb26aa12a288bd58e11f811aae3..6783a7edbb672ef70e00d3684e3f35427ea12eab 100644 (file)
@@ -3926,7 +3926,9 @@ array_creation_expression
                if ($4 == null)
                        report.Error (1586, GetLocation ($1), "Array creation must have array size or array initializer");
 
-               $$ = new ArrayCreation ((FullNamedExpression) $2, (ComposedTypeSpecifier) $3, (ArrayInitializer) $4, GetLocation ($1));
+               $$ = new ArrayCreation ((FullNamedExpression) $2, (ComposedTypeSpecifier) $3, (ArrayInitializer) $4, GetLocation ($1)) {
+                       NoEmptyInterpolation = true
+               };
          }
        | NEW rank_specifier array_initializer
          {
index 8553856ac585229093f9edb551cd9f993ce78276..4a0e4af6fc896df171530249f820649ebb8df0d5 100644 (file)
@@ -535,7 +535,7 @@ namespace Mono.CSharp {
 
                void ResolveConditionalAccessReceiver (ResolveContext rc)
                {
-                       // LAMESPEC: Not sure why this is explicitly disalloed with very odd error message
+                       // LAMESPEC: Not sure why this is explicitly disallowed with very odd error message
                        if (!rc.HasSet (ResolveContext.Options.DontSetConditionalAccessReceiver) && method_group.HasConditionalAccess ()) {
                                Error_OperatorCannotBeApplied (rc, loc, "?", method_group.Type);
                        }
index a581906d3e9b82d7ffd04ab74c4c1f8275e7efa5..fc99defc44e19359646b879d59bb7feb63bba902 100644 (file)
@@ -469,8 +469,13 @@ namespace Mono.CSharp {
                        return false;
                }
 
-               protected static TypeSpec LiftMemberType (ResolveContext rc, TypeSpec type)
+               protected TypeSpec LiftMemberType (ResolveContext rc, TypeSpec type)
                {
+                       var tps = type as TypeParameterSpec;
+                       if (tps != null && !(tps.IsReferenceType || tps.IsValueType)) {
+                               Error_OperatorCannotBeApplied (rc, loc, "?", type);
+                       }
+
                        return TypeSpec.IsValueType (type) && !type.IsNullableType ?
                                Nullable.NullableInfo.MakeType (rc.Module, type) :
                                type;
@@ -1332,7 +1337,7 @@ namespace Mono.CSharp {
                {
                }
 
-               public ExpressionStatement ResolveStatement (BlockContext ec)
+               public virtual ExpressionStatement ResolveStatement (BlockContext ec)
                {
                        Expression e = Resolve (ec);
                        if (e == null)
@@ -4647,7 +4652,7 @@ namespace Mono.CSharp {
                ///     false if candidate ain't better
                ///     true  if candidate is better than the current best match
                /// </remarks>
-               static bool BetterFunction (ResolveContext ec, Arguments args, MemberSpec candidate, AParametersCollection cparam, bool candidate_params,
+               bool BetterFunction (ResolveContext ec, Arguments args, MemberSpec candidate, AParametersCollection cparam, bool candidate_params,
                        MemberSpec best, AParametersCollection bparam, bool best_params)
                {
                        AParametersCollection candidate_pd = ((IParametersMember) candidate).Parameters;
@@ -4704,8 +4709,20 @@ namespace Mono.CSharp {
 
                                // for each argument, the conversion to 'ct' should be no worse than 
                                // the conversion to 'bt'.
-                               if (result == 2)
-                                       return false;
+                               if (result == 2) {
+                                       //
+                                       // No optional parameters tie breaking rules for delegates overload resolution
+                                       //
+                                       if ((this.restrictions & Restrictions.CovariantDelegate) != 0)
+                                               return false;
+
+                                       better_at_least_one = false;
+
+                                       ++j;
+                                       while (j < args_count && !args [j++].IsDefaultArgument) ;
+
+                                       break;
+                               }
 
                                // for at least one argument, the conversion to 'ct' should be better than 
                                // the conversion to 'bt'.
@@ -4717,15 +4734,26 @@ namespace Mono.CSharp {
                                return true;
 
                        //
-                       // Tie-breaking rules are applied only for equivalent parameter types
+                       // LAMESPEC: Tie-breaking rules for not equivalent parameter types
                        //
                        if (!are_equivalent) {
                                //
-                               // LAMESPEC: A candidate with less default parameters is still better when there
+                               // A candidate with no default parameters is still better when there
                                // is no better expression conversion
                                //
-                               if (candidate_pd.Count < best_pd.Count && !candidate_params && best_pd.FixedParameters [j].HasDefaultValue) {
-                                       return true;
+                               if (candidate_pd.Count < best_pd.Count) {
+                                       if (!candidate_params && !candidate_pd.FixedParameters [j - j].HasDefaultValue) {
+                                               return true;
+                                       }
+                               } else if (candidate_pd.Count == best_pd.Count) {
+                                       if (candidate_params)
+                                               return false;
+
+                                       if (!candidate_pd.FixedParameters [j - 1].HasDefaultValue && best_pd.FixedParameters [j - 1].HasDefaultValue)
+                                               return true;
+
+                                       if (candidate_pd.FixedParameters [j - 1].HasDefaultValue && best_pd.HasParams)
+                                               return true;
                                }
 
                                return false;
@@ -4746,7 +4774,7 @@ namespace Mono.CSharp {
                                var cand_param = candidate_pd.FixedParameters [j];
                                var best_param = best_pd.FixedParameters [j];
 
-                               if (cand_param.HasDefaultValue != best_param.HasDefaultValue)
+                               if (cand_param.HasDefaultValue != best_param.HasDefaultValue && (!candidate_pd.HasParams || !best_pd.HasParams))
                                        return cand_param.HasDefaultValue;
 
                                defaults_ambiguity = true;
index bfba44fbb8c656079254fc346737ea8a4af5fd3e..aadf818066d2ad89b3d82a2b8488256753e09d9c 100644 (file)
@@ -7023,6 +7023,16 @@ namespace Mono.CSharp
                        }
                }
 
+               bool statement_resolve;
+               public override ExpressionStatement ResolveStatement (BlockContext bc)
+               {
+                       statement_resolve = true;
+                       var es = base.ResolveStatement (bc);
+                       statement_resolve = false;
+
+                       return es;
+               }
+
                protected override Expression DoResolve (ResolveContext rc)
                {
                        ResolveConditionalAccessReceiver (rc);
@@ -7111,7 +7121,7 @@ namespace Mono.CSharp
 
                        var method = mg.BestCandidate;
                        type = mg.BestCandidateReturnType;
-                       if (conditional_access_receiver)
+                       if (conditional_access_receiver && !statement_resolve)
                                type = LiftMemberType (ec, type);
 
                        if (arguments == null && method.DeclaringType.BuiltinType == BuiltinTypeSpec.Type.Object && method.Name == Destructor.MetadataName) {
@@ -7173,7 +7183,7 @@ namespace Mono.CSharp
                                                args.Insert (0, new Argument (inst.Resolve (ec), mod));
                                        }
                                } else {        // is SimpleName
-                                       if (ec.IsStatic) {
+                                       if (ec.IsStatic || ec.HasAny (ResolveContext.Options.FieldInitializerScope | ResolveContext.Options.BaseInitializer)) {
                                                args.Insert (0, new Argument (new TypeOf (ec.CurrentType, loc).Resolve (ec), Argument.AType.DynamicTypeName));
                                        } else {
                                                args.Insert (0, new Argument (new This (loc).Resolve (ec)));
@@ -7862,6 +7872,8 @@ namespace Mono.CSharp
                {
                }
 
+               public bool NoEmptyInterpolation { get; set; }
+
                public ComposedTypeSpecifier Rank {
                        get {
                                return this.rank;
@@ -8398,11 +8410,32 @@ namespace Mono.CSharp
 
                public override void Emit (EmitContext ec)
                {
+                       if (!NoEmptyInterpolation && EmitOptimizedEmpty (ec))
+                               return;
+
                        var await_field = EmitToFieldSource (ec);
                        if (await_field != null)
                                await_field.Emit (ec);
                }
 
+               bool EmitOptimizedEmpty (EmitContext ec)
+               {
+                       if (arguments.Count != 1 || dimensions != 1)
+                               return false;
+
+                       var c = arguments [0] as Constant;
+                       if (c == null || !c.IsZeroInteger)
+                               return false;
+
+                       var m = ec.Module.PredefinedMembers.ArrayEmpty.Get ();
+                       if (m == null || ec.CurrentType.MemberDefinition.DeclaringAssembly == m.DeclaringType.MemberDefinition.DeclaringAssembly)
+                               return false;
+
+                       m = m.MakeGenericMethod (ec.MemberContext, array_element_type);
+                       ec.Emit (OpCodes.Call, m);
+                       return true;
+               }
+
                protected sealed override FieldExpr EmitToFieldSource (EmitContext ec)
                {
                        if (first_emit != null) {
index df43ff38e8e09f0387a6810ad441a6d56c5d8457..47919ec8ce2b5fda133bddbb93509096ba9ef671 100644 (file)
@@ -30,6 +30,7 @@ namespace Mono.CSharp
                protected T machine_initializer;
                int resume_pc;
                ExceptionStatement inside_try_block;
+               TryCatch inside_catch_block;
 
                protected YieldStatement (Expression expr, Location l)
                {
@@ -69,6 +70,7 @@ namespace Mono.CSharp
 
                        machine_initializer = bc.CurrentAnonymousMethod as T;
                        inside_try_block = bc.CurrentTryBlock;
+                       inside_catch_block = bc.CurrentTryCatch;
                        return true;
                }
 
@@ -80,7 +82,7 @@ namespace Mono.CSharp
                        if (inside_try_block == null) {
                                resume_pc = machine_initializer.AddResumePoint (this);
                        } else {
-                               resume_pc = inside_try_block.AddResumePoint (this, resume_pc, machine_initializer);
+                               resume_pc = inside_try_block.AddResumePoint (this, resume_pc, machine_initializer, inside_catch_block);
                                unwind_protect = true;
                                inside_try_block = null;
                        }
index 16a67f4cbd9cb446147670c989887cef81f56c17..0c199017af9b1d4e3e19624afb3563ee9b7705ca 100644 (file)
@@ -1211,13 +1211,29 @@ namespace Mono.CSharp {
                                return ParseResult.Success;
 
                        // csc options that we don't support
-                       case "/utf8output":
-                       case "/subsystemversion":
+                       case "/analyzer":
+                       case "/appconfig":
+                       case "/baseaddress":
+                       case "/deterministic":
+                       case "/errorendlocation":
+                       case "/errorlog":
+                       case "/features":
                        case "/highentropyva":
                        case "/highentropyva+":
                        case "/highentropyva-":
-                       case "/win32manifest":
+                       case "/link":
+                       case "/moduleassemblyname":
                        case "/nowin32manifest":
+                       case "/pathmap":
+                       case "/pdb":
+                       case "/preferreduilang":
+                       case "/publicsign":
+                       case "/reportanalyzer":
+                       case "/ruleset":
+                       case "/sqmsessionguid":
+                       case "/subsystemversion":
+                       case "/utf8output":
+                       case "/win32manifest":
                                return ParseResult.Success;
 
                        default:
index 9c84398ee3e4d52c01e8a3d25fd83adff75e96e3..d0341cb3b633045c48889bfa3a3f31789df36ff0 100644 (file)
@@ -5877,7 +5877,7 @@ namespace Mono.CSharp {
                protected override bool DoFlowAnalysis (FlowAnalysisContext fc)
                {
                        var res = stmt.FlowAnalysis (fc);
-                       parent = null;
+                       parent_try_block = null;
                        return res;
                }
 
@@ -5897,14 +5897,18 @@ namespace Mono.CSharp {
                {
                        bool ok;
 
-                       parent = bc.CurrentTryBlock;
+                       parent_try_block = bc.CurrentTryBlock;
                        bc.CurrentTryBlock = this;
 
-                       using (bc.Set (ResolveContext.Options.TryScope)) {
+                       if (stmt is TryCatch) {
                                ok = stmt.Resolve (bc);
+                       } else {
+                               using (bc.Set (ResolveContext.Options.TryScope)) {
+                                       ok = stmt.Resolve (bc);
+                               }
                        }
 
-                       bc.CurrentTryBlock = parent;
+                       bc.CurrentTryBlock = parent_try_block;
 
                        //
                        // Finally block inside iterator is called from MoveNext and
@@ -5930,18 +5934,14 @@ namespace Mono.CSharp {
        {
                protected List<ResumableStatement> resume_points;
                protected int first_resume_pc;
-               protected ExceptionStatement parent;
+               protected ExceptionStatement parent_try_block;
+               protected int first_catch_resume_pc = -1;
 
                protected ExceptionStatement (Location loc)
                {
                        this.loc = loc;
                }
 
-               protected virtual void EmitBeginException (EmitContext ec)
-               {
-                       ec.BeginExceptionBlock ();
-               }
-
                protected virtual void EmitTryBodyPrepare (EmitContext ec)
                {
                        StateMachineInitializer state_machine = null;
@@ -5952,10 +5952,37 @@ namespace Mono.CSharp {
                                ec.Emit (OpCodes.Stloc, state_machine.CurrentPC);
                        }
 
-                       EmitBeginException (ec);
+                       //
+                       // The resume points in catch section when this is try-catch-finally
+                       //
+                       if (IsRewrittenTryCatchFinally ()) {
+                               ec.BeginExceptionBlock ();
+
+                               if (first_catch_resume_pc >= 0) {
 
-                       if (resume_points != null) {
-                               ec.MarkLabel (resume_point);
+                                       ec.MarkLabel (resume_point);
+
+                                       // For normal control flow, we want to fall-through the Switch
+                                       // So, we use CurrentPC rather than the $PC field, and initialize it to an outside value above
+                                       ec.Emit (OpCodes.Ldloc, state_machine.CurrentPC);
+                                       ec.EmitInt (first_resume_pc + first_catch_resume_pc);
+                                       ec.Emit (OpCodes.Sub);
+
+                                       var labels = new Label [resume_points.Count - first_catch_resume_pc];
+                                       for (int i = 0; i < labels.Length; ++i)
+                                               labels [i] = resume_points [i + first_catch_resume_pc].PrepareForEmit (ec);
+                                       ec.Emit (OpCodes.Switch, labels);
+                               }
+                       }
+
+                       ec.BeginExceptionBlock ();
+
+                       //
+                       // The resume points for try section
+                       //
+                       if (resume_points != null && first_catch_resume_pc != 0) {
+                               if (first_catch_resume_pc < 0)
+                                       ec.MarkLabel (resume_point);
 
                                // For normal control flow, we want to fall-through the Switch
                                // So, we use CurrentPC rather than the $PC field, and initialize it to an outside value above
@@ -5963,21 +5990,30 @@ namespace Mono.CSharp {
                                ec.EmitInt (first_resume_pc);
                                ec.Emit (OpCodes.Sub);
 
-                               Label[] labels = new Label[resume_points.Count];
-                               for (int i = 0; i < resume_points.Count; ++i)
+                               var labels = new Label[resume_points.Count - System.Math.Max (first_catch_resume_pc, 0)];
+                               for (int i = 0; i < labels.Length; ++i)
                                        labels[i] = resume_points[i].PrepareForEmit (ec);
                                ec.Emit (OpCodes.Switch, labels);
                        }
                }
 
-               public virtual int AddResumePoint (ResumableStatement stmt, int pc, StateMachineInitializer stateMachine)
+               bool IsRewrittenTryCatchFinally ()
                {
-                       if (parent != null) {
-                               // TODO: MOVE to virtual TryCatch
-                               var tc = this as TryCatch;
-                               var s = tc != null && tc.IsTryCatchFinally ? stmt : this;
+                       var tf = this as TryFinally;
+                       if (tf == null)
+                               return false;
+
+                       var tc = tf.Statement as TryCatch;
+                       if (tc == null)
+                               return false;
 
-                               pc = parent.AddResumePoint (s, pc, stateMachine);
+                       return tf.FinallyBlock.HasAwait || tc.HasClauseWithAwait;
+               }
+
+               public int AddResumePoint (ResumableStatement stmt, int pc, StateMachineInitializer stateMachine, TryCatch catchBlock)
+               {
+                       if (parent_try_block != null) {
+                               pc = parent_try_block.AddResumePoint (this, pc, stateMachine, catchBlock);
                        } else {
                                pc = stateMachine.AddResumePoint (this);
                        }
@@ -5990,6 +6026,11 @@ namespace Mono.CSharp {
                        if (pc != first_resume_pc + resume_points.Count)
                                throw new InternalErrorException ("missed an intervening AddResumePoint?");
 
+                       var tf = this as TryFinally;
+                       if (tf != null && tf.Statement == catchBlock && first_catch_resume_pc < 0) {
+                               first_catch_resume_pc = resume_points.Count;
+                       }
+
                        resume_points.Add (stmt);
                        return pc;
                }
@@ -6936,14 +6977,6 @@ namespace Mono.CSharp {
                        return ok;
                }
 
-               protected override void EmitBeginException (EmitContext ec)
-               {
-                       if (fini.HasAwait && stmt is TryCatch)
-                               ec.BeginExceptionBlock ();
-
-                       base.EmitBeginException (ec);
-               }
-
                protected override void EmitTryBody (EmitContext ec)
                {
                        if (fini.HasAwait) {
@@ -6953,7 +6986,7 @@ namespace Mono.CSharp {
                                ec.TryFinallyUnwind.Add (this);
                                stmt.Emit (ec);
 
-                               if (stmt is TryCatch)
+                               if (first_catch_resume_pc < 0 && stmt is TryCatch)
                                        ec.EndExceptionBlock ();
 
                                ec.TryFinallyUnwind.Remove (this);
@@ -7193,6 +7226,12 @@ namespace Mono.CSharp {
                        }
                }
 
+               public bool HasClauseWithAwait {
+                       get {
+                               return catch_sm != null;
+                       }
+               }
+
                public bool IsTryCatchFinally {
                        get {
                                return inside_try_finally;
@@ -7204,7 +7243,8 @@ namespace Mono.CSharp {
                        bool ok;
 
                        using (bc.Set (ResolveContext.Options.TryScope)) {
-                               parent = bc.CurrentTryBlock;
+
+                               parent_try_block = bc.CurrentTryBlock;
 
                                if (IsTryCatchFinally) {
                                        ok = Block.Resolve (bc);
@@ -7212,11 +7252,14 @@ namespace Mono.CSharp {
                                        using (bc.Set (ResolveContext.Options.TryWithCatchScope)) {
                                                bc.CurrentTryBlock = this;
                                                ok = Block.Resolve (bc);
-                                               bc.CurrentTryBlock = parent;
+                                               bc.CurrentTryBlock = parent_try_block;
                                        }
                                }
                        }
 
+                       var prev_catch = bc.CurrentTryCatch;
+                       bc.CurrentTryCatch = this;
+
                        for (int i = 0; i < clauses.Count; ++i) {
                                var c = clauses[i];
 
@@ -7275,6 +7318,8 @@ namespace Mono.CSharp {
                                }
                        }
 
+                       bc.CurrentTryCatch = prev_catch;
+
                        return base.Resolve (bc) && ok;
                }
 
@@ -7307,10 +7352,12 @@ namespace Mono.CSharp {
                                }
                        }
 
-                       if (!inside_try_finally)
+                       if (state_variable == null) {
+                               if (!inside_try_finally)
+                                       ec.EndExceptionBlock ();
+                       } else {
                                ec.EndExceptionBlock ();
 
-                       if (state_variable != null) {
                                ec.Emit (OpCodes.Ldloc, state_variable);
 
                                var labels = new Label [catch_sm.Count + 1];
@@ -7362,7 +7409,7 @@ namespace Mono.CSharp {
                        }
 
                        fc.DefiniteAssignment = try_fc ?? start_fc;
-                       parent = null;
+                       parent_try_block = null;
                        return res;
                }
 
index a5a9ad15607da053892c5073fee28ecfcdd25130..b53915f6eb1c030c749d98c239553e8a7c46c76d 100644 (file)
@@ -198,6 +198,8 @@ namespace Mono.CSharp
                public readonly PredefinedType SecurityAction;
                public readonly PredefinedType Dictionary;
                public readonly PredefinedType Hashtable;
+               public readonly PredefinedType Array;
+
                public readonly TypeSpec[] SwitchUserTypes;
 
                //
@@ -266,6 +268,7 @@ namespace Mono.CSharp
                        SecurityAction = new PredefinedType (module, MemberKind.Enum, "System.Security.Permissions", "SecurityAction");
                        Dictionary = new PredefinedType (module, MemberKind.Class, "System.Collections.Generic", "Dictionary", 2);
                        Hashtable = new PredefinedType (module, MemberKind.Class, "System.Collections", "Hashtable");
+                       Array = new PredefinedType (module, MemberKind.Class, "System", "Array");
 
                        Expression = new PredefinedType (module, MemberKind.Class, "System.Linq.Expressions", "Expression");
                        ExpressionGeneric = new PredefinedType (module, MemberKind.Class, "System.Linq.Expressions", "Expression", 1);
@@ -340,6 +343,7 @@ namespace Mono.CSharp
        class PredefinedMembers
        {
                public readonly PredefinedMember<MethodSpec> ActivatorCreateInstance;
+               public readonly PredefinedMember<MethodSpec> ArrayEmpty;
                public readonly PredefinedMember<MethodSpec> AsyncTaskMethodBuilderCreate;
                public readonly PredefinedMember<MethodSpec> AsyncTaskMethodBuilderStart;
                public readonly PredefinedMember<MethodSpec> AsyncTaskMethodBuilderSetResult;
@@ -411,6 +415,9 @@ namespace Mono.CSharp
                        ActivatorCreateInstance = new PredefinedMember<MethodSpec> (module, types.Activator,
                                MemberFilter.Method ("CreateInstance", 1, ParametersCompiled.EmptyReadOnlyParameters, null));
 
+                       ArrayEmpty = new PredefinedMember<MethodSpec> (module, types.Array,
+                               MemberFilter.Method ("Empty", 1, ParametersCompiled.EmptyReadOnlyParameters, null));
+
                        AsyncTaskMethodBuilderCreate = new PredefinedMember<MethodSpec> (module, types.AsyncTaskMethodBuilder,
                                MemberFilter.Method ("Create", 0, ParametersCompiled.EmptyReadOnlyParameters, types.AsyncTaskMethodBuilder.TypeSpec));
 
index 81894f06c762ea1d6146e2e9d99905b2d3a7f4e1..fb02370dbb32cd2317827d323637b370d01e0048 100644 (file)
@@ -547,7 +547,15 @@ namespace Mono.CSharp
 
                public string GetSignatureForErrorIncludingAssemblyName ()
                {
-                       return string.Format ("{0} [{1}]", GetSignatureForError (), MemberDefinition.DeclaringAssembly.FullName);
+                       var imported = MemberDefinition.DeclaringAssembly as ImportedAssemblyDefinition;
+
+                       var location = imported != null ?
+                               System.IO.Path.GetFullPath (imported.Location) :
+                           ((MemberCore)MemberDefinition).Location.NameFullPath;
+
+                       return string.Format ("{0} [{1} -- {2}]", GetSignatureForError (),
+                                                                 MemberDefinition.DeclaringAssembly.FullName,
+                                                                 location);
                }
 
                protected virtual string GetTypeNameSignature ()
index fe0910186fe43ff3478be0db86d691b9c471a492..7a291b287a7c04caaf70e006548829969cec067b 100644 (file)
@@ -5,11 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.util.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LOCAL_MCS_FLAGS= \
-       /resource:Transform.resources,NUnit.Util.Transform.resources \
-       -r:nunit.core.dll -r:nunit.core.interfaces.dll -r:System.dll \
-       -r:System.Xml.dll -r:System.Runtime.Remoting.dll \
-       /d:MONO /d:StronglyNamedAssembly -warn:1
+LOCAL_MCS_FLAGS= /resource:Transform.resources,NUnit.Util.Transform.resources /d:MONO /d:StronglyNamedAssembly /publicsign -warn:1
+LIB_REFS = nunit.core nunit.core.interfaces System System.Xml System.Runtime.Remoting
 NO_TEST = yo
 
 RESX_RES = Transform.resources
index b09931ffef6cec8e1811c8954abed8a4f3817796..72ce02dc4295faebb9c8a9d525c059e9493dc9dc 100644 (file)
@@ -3,9 +3,9 @@ SUBDIRS =
 include ../../../build/rules.make
 
 PROGRAM = nunit-console.exe
-LOCAL_MCS_FLAGS = \
-       /r:nunit.framework.dll /r:nunit.util.dll /r:nunit.core.dll \
-       /r:nunit-console-runner.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = nunit.framework nunit.util nunit.core nunit-console-runner
+
 EXTRA_DISTFILES = App.ico \
        nunit-console.exe.csproj \
        nunit-console.exe_VS2005.csproj \
index 52fe21bf61bd20ba7b9146cb190bff2faef5d5d3..b72165aba26d29183205711c97bd0578739e191b 100644 (file)
@@ -5,10 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit-console-runner.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LOCAL_MCS_FLAGS= \
-       -r:nunit.core.dll -r:nunit.core.interfaces.dll -r:nunit.util.dll \
-       -r:System.dll -r:System.Xml.dll \
-       /d:MONO /d:StronglyNamedAssembly
+LOCAL_MCS_FLAGS= /d:MONO /d:StronglyNamedAssembly /publicsign
+LIB_REFS = nunit.core nunit.core.interfaces nunit.util System System.Xml
 NO_TEST = yo
 
 EXTRA_DISTFILES = nunit-console.csproj nunit-console_VS2005.csproj
index ac3b0146fbfb99fc9f9ecb04302b6c3fed65fd3d..83a2e01bd0e038c550791c58e54b57bdbe203305 100644 (file)
@@ -5,7 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.core.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LOCAL_MCS_FLAGS= -r:nunit.framework.dll -r:nunit.core.interfaces.dll -r:System.dll /d:StronglyNamedAssembly -warn:1
+LOCAL_MCS_FLAGS = /d:StronglyNamedAssembly -warn:1 /publicsign
+LIB_REFS = nunit.framework nunit.core.interfaces System
 NO_TEST = yo
 
 EXTRA_DISTFILES = nunit.core.dll.csproj nunit.core.dll_VS2005.csproj
index e9ddcc79faffa2990629eb1ecd221fb850e39243..592ce5bc160609434cccbf45e3a41e9473fbefe8 100644 (file)
@@ -5,7 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.core.interfaces.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LOCAL_MCS_FLAGS= -debug -r:nunit.framework.dll -r:System.dll /d:StronglyNamedAssembly
+LOCAL_MCS_FLAGS= /d:StronglyNamedAssembly /publicsign
+LIB_REFS = nunit.framework System
 NO_TEST = yo
 
 EXTRA_DISTFILES = nunit.core.interfaces.dll.csproj nunit.core.interfaces.dll_VS2005.csproj
index 48f8ccf8f6fddb1a8a87d0838ab0c888fb9cefad..9e3ba945a67a7904b0ea369ab0a7509b581c9471 100644 (file)
@@ -5,10 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.core.extensions.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LIB_MCS_FLAGS = \
-       -debug \
-       /r:nunit.core.dll /r:nunit.core.interfaces.dll \
-       /r:System.Xml.dll /r:System.dll /d:StronglyNamedAssembly
+LIB_MCS_FLAGS =  /d:StronglyNamedAssembly /publicsign
+LIB_REFS = nunit.core nunit.core.interfaces System.Xml System
 NO_TEST = yo
 
 EXTRA_DISTFILES = \
index 81d6b15439d091dc1e5fd4e99e4d3d3e2bd97b1d..7cd03514e37831f9193f83dbffccd4de19cf5434 100644 (file)
@@ -5,7 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.framework.extensions.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LIB_MCS_FLAGS = -debug /r:System.Xml.dll /r:System.dll /d:StronglyNamedAssembly
+LIB_MCS_FLAGS = /d:StronglyNamedAssembly /publicsign
+LIB_REFS = System.Xml System
 NO_TEST = yo
 
 EXTRA_DISTFILES = \
index 157b0b4d5783cf517eb9e8d38508d7df8bc08e95..43076d8c8553ae0954ad041a6b77b9286e9ae6b1 100644 (file)
@@ -6,7 +6,8 @@ LIBRARY = NUnit.Framework.dll
 LIBRARY_NAME = nunit.framework.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LIB_MCS_FLAGS = /r:System.Xml.dll /r:System.dll /d:StronglyNamedAssembly -warn:1
+LIB_MCS_FLAGS = /d:StronglyNamedAssembly -warn:1 /publicsign
+LIB_REFS = System.Xml System
 NO_TEST = yo
 
 EXTRA_DISTFILES = \
index b9769c4777d6576f992949c24bf4e893ec3df3bd..0c6ab3ca272cd9f41a757fe80c2b2a22149c51da 100644 (file)
@@ -5,7 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunit.mocks.dll
 LIBRARY_SNK = $(topdir)/nunit24/nunit.snk
 
-LOCAL_MCS_FLAGS= -debug -r:nunit.framework.dll -r:System.dll /d:StronglyNamedAssembly
+LOCAL_MCS_FLAGS= /d:StronglyNamedAssembly /publicsign
+LIB_REFS = nunit.framework System
 NO_TEST = yo
 
 EXTRA_DISTFILES = \
diff --git a/mcs/tests/dtest-064.cs b/mcs/tests/dtest-064.cs
new file mode 100644 (file)
index 0000000..da593f6
--- /dev/null
@@ -0,0 +1,46 @@
+using System;
+
+public class A
+{
+       public A (Action action)
+       {
+       }
+}
+
+public class B : A
+{
+       public B () 
+               : base (() => {
+                       dynamic d = 1;
+                       Test (d);
+               })
+       {
+       }
+
+       static decimal Test (dynamic arg)
+       {
+               return 3m;
+       }
+}
+
+public class B2
+{
+       public Action a = () => {
+                       dynamic d = 1;
+                       Test (d);
+               };
+
+       static decimal Test (dynamic arg)
+       {
+               return 3m;
+       }
+}
+
+class M
+{
+       static void Main ()
+       {
+               new B ();
+               new B2 ();
+       }       
+}
\ No newline at end of file
index 7117ab291e7ce6b4fed42288979c4a60936c1279..9ed101f55221f9dd6473518cee7ab70a0fe27795 100644 (file)
@@ -104,10 +104,10 @@ public class Program
                if (Test_5 () != 0)
                        return 5;
 
-               if (Test_6 () != 0)
+               if (Test_6 () != 1)
                        return 6;
 
-               if (Test_7 (false) != 0)
+               if (Test_7 (false) != 1)
                        return 7;
 
                if (Test_8 (typeof (bool)) != 0)
diff --git a/mcs/tests/gtest-optional-36.cs b/mcs/tests/gtest-optional-36.cs
new file mode 100644 (file)
index 0000000..bf9f7d1
--- /dev/null
@@ -0,0 +1,66 @@
+using System;
+
+public class Program
+{
+       static int Arg (uint a, long b)
+       {
+               return 2;
+       }
+
+       static int Arg (int a, ulong b, int c = 9)
+       {
+               return 3;
+       }
+
+       static int Arg_2 (uint a, long b, params int[] arg)
+       {
+               return 2;
+       }
+
+       static int Arg_2 (int a, ulong b, int c = 0)
+       {
+               return 3;
+       }
+
+       static int Arg_3 (int a, long b, params int[] arg)
+       {
+               return 2;
+       }
+
+       static int Arg_3 (uint a, ulong b, int c = 0, int d = 1, params int[] oo)
+       {
+               return 3;
+       }       
+
+       public static int Main ()
+       {
+               if (Arg (0, 0) != 2)
+                       return 1;
+
+               if (Arg (0, 0, 0) != 3)
+                       return 2;
+
+               if (Arg_2 (0, 0) != 3)
+                       return 3;
+
+               if (Arg_2 (0, 0, 0, 0) != 2)
+                       return 4;
+
+               if (Arg_3 (0, 0) != 2)
+                       return 5;
+
+               if (Arg_3 (0, 0, 0) != 2)
+                       return 6;
+
+               if (Arg_3 (0, 0, 0, 0) != 2)
+                       return 7;
+
+               if (Arg_3 (0, 0, 0, 0, 0) != 2)
+                       return 8;
+
+               if (Arg_3 (0, 0, 0, 0, 0) != 2)
+                       return 9;
+
+               return 0;
+       }
+}
diff --git a/mcs/tests/gtest-optional-37.cs b/mcs/tests/gtest-optional-37.cs
new file mode 100644 (file)
index 0000000..f322ff6
--- /dev/null
@@ -0,0 +1,19 @@
+using System;
+
+class Test1
+{
+       static object Foo (int arg = 1, int arg2 = 2)
+       {
+               return null;
+       }
+
+       static object Foo (object arg, object arg2)
+       {
+               return null;
+       }
+
+       public static void Main ()
+       {
+               Func<int, int, object> o = Foo;
+       }
+}
\ No newline at end of file
diff --git a/mcs/tests/test-933.cs b/mcs/tests/test-933.cs
new file mode 100644 (file)
index 0000000..2f076eb
--- /dev/null
@@ -0,0 +1,22 @@
+using System;
+
+class X
+{
+       static int Foo (params X[] p)
+       {
+               return 1;
+       }
+
+       static int Foo (object p)
+       {
+               return 0;
+       }
+
+       static int Main ()
+       {
+               if (Foo ((X[]) null) != 1)
+                       return 1;
+
+               return 0;
+       }
+}
\ No newline at end of file
diff --git a/mcs/tests/test-934.cs b/mcs/tests/test-934.cs
new file mode 100644 (file)
index 0000000..ba464e3
--- /dev/null
@@ -0,0 +1,22 @@
+class X
+{
+       public static int Main ()
+       {
+               var a = new byte[] { };
+               var b = new byte[] { };
+               if (a.Equals (b))
+                       return 1;
+
+               if (ReferenceEquals (a, b))
+                       return 2;
+
+               b = new byte[0];
+               if (a.Equals (b))
+                       return 3;
+
+               if (ReferenceEquals (a, b))
+                       return 4;
+
+               return 0;
+       }
+}
\ No newline at end of file
diff --git a/mcs/tests/test-async-85.cs b/mcs/tests/test-async-85.cs
new file mode 100644 (file)
index 0000000..36c7a1e
--- /dev/null
@@ -0,0 +1,74 @@
+using System;
+using System.Threading.Tasks;
+
+class Program
+{
+       static int count;
+
+       static int Main ()
+       {
+               Test (false).Wait ();
+               Console.WriteLine (count);
+               if (count != 110011)
+                       return 1;
+
+               count = 0;
+               Test (true).Wait ();
+               Console.WriteLine (count);
+               if (count != 111101)
+                       return 2;
+
+               count = 0;
+               Test2 (false).Wait ();
+               Console.WriteLine (count);
+               if (count != 11)
+                       return 3;
+
+               count = 0;
+               Test2 (true).Wait ();
+               Console.WriteLine (count);
+               if (count != 1101)
+                       return 4;
+
+               return 0;
+       }
+
+       static async Task Test (bool throwTest)
+       {
+               try {
+                       count += 1;
+                       await Task.Delay (10);
+
+                       if (throwTest)
+                               throw new ApplicationException ();
+
+                       count += 10;
+               } catch (ApplicationException) {
+                       count += 100;
+                       await Task.Delay (10);
+                       count += 1000;
+               } finally {
+                       count += 10000;
+                       await Task.Delay (10);
+                       count += 100000;
+               }
+       }
+
+       static async Task Test2 (bool throwTest)
+       {
+               try {
+                       count += 1;
+                       await Task.Delay (10);
+
+                       if (throwTest)
+                               throw new ApplicationException ();
+
+                       count += 10;
+               } catch (ApplicationException) {
+                       count += 100;
+                       await Task.Delay (10);
+                       count += 1000;
+               } finally {
+               }
+       }       
+}
index 8c966ef91e8f63f76b24bf0f422a520846f0427b..9b087dd751dae78098aa36a6d2e2a9dd66680e7f 100644 (file)
@@ -38,9 +38,9 @@
         <entry il="0x0" row="20" col="2" file_ref="1" hidden="false" />
         <entry il="0x1" row="21" col="3" file_ref="1" hidden="false" />
         <entry il="0x11" row="21" col="59" file_ref="1" hidden="false" />
-        <entry il="0x1c" row="21" col="53" file_ref="1" hidden="false" />
-        <entry il="0x2c" row="21" col="47" file_ref="1" hidden="false" />
-        <entry il="0x32" row="22" col="2" file_ref="1" hidden="false" />
+        <entry il="0x1b" row="21" col="53" file_ref="1" hidden="false" />
+        <entry il="0x2a" row="21" col="47" file_ref="1" hidden="false" />
+        <entry il="0x30" row="22" col="2" file_ref="1" hidden="false" />
       </sequencepoints>
       <locals>
         <entry name="e" il_index="0" scope_ref="0" />
index ea92d6af0de4bb188050d29921e7dc39cb32227d..4ad5cdf547e8c744dbad0e1b154e95d8ce16d2d0 100644 (file)
@@ -29,6 +29,11 @@ public class MainClass
        public static event Action Act = null;
        public static dynamic BBB = null;
 
+       void ParameterTest (Person ParPerson)
+       {
+               Console.WriteLine (nameof (ParPerson.MyCar.Year));
+       }
+
        public static int Main ()
        {
                string name;
@@ -61,6 +66,11 @@ public class MainClass
                if (name != "ToString")
                        return 7;
 
+               Person LocPerson = null;
+               name = nameof (LocPerson.MyCar.Year);
+               if (name != "Year")
+                       return 8;
+
                return 0;
        }
 }
diff --git a/mcs/tests/test-null-operator-04.cs b/mcs/tests/test-null-operator-04.cs
new file mode 100644 (file)
index 0000000..c28aa17
--- /dev/null
@@ -0,0 +1,55 @@
+using System;
+
+interface IFoo<T>
+{
+       T Call ();
+}
+
+class C1
+{
+       public void Foo<T> (IFoo<T> t) where T : class
+       {
+               t?.Call ();
+               var x = t?.Call ();
+       }
+
+       public void Foo2<T> (IFoo<T> t)
+       {
+               t?.Call ();
+       }       
+}
+
+class C2<T> where T : class
+{
+       C2<T> i;
+       T field;
+
+       public void Foo ()
+       {
+               var x = i?.field;
+       }
+}
+
+class Program
+{
+       static void Test<T>(Func<T> func) where T : struct
+       {
+               var r = func?.Invoke ();
+       }
+
+       static void Test2<T>(Func<T> func)
+       {
+               func?.Invoke ();
+       }
+
+       static void Main()
+       {
+               new C1 ().Foo<Program> (null);
+               new C1 ().Foo2<Program> (null);
+
+               new C2<string> ().Foo ();
+
+               Test (() => 1);
+               Test (() => 2);
+       }
+}
\ No newline at end of file
index 3cc0ea315382acaa4f7e2726f79714b6d3bab297..027fd9871ef422bf008dc6f7e66ff4196ed13027 100644 (file)
@@ -85,7 +85,7 @@
   <test name="dtest-003.cs">
     <type name="AssertDynamicObject">
       <method name="System.Dynamic.DynamicMetaObject GetFakeMetaObject(System.Object)" attrs="129">
-        <size>130</size>
+        <size>129</size>
       </method>
       <method name="System.Dynamic.DynamicMetaObject BindBinaryOperation(System.Dynamic.BinaryOperationBinder, System.Dynamic.DynamicMetaObject)" attrs="198">
         <size>70</size>
     </type>
     <type name="Tester+&lt;GetIndex_3&gt;c__AnonStorey1">
       <method name="Void &lt;&gt;m__0(System.Dynamic.GetIndexBinder, System.Object[])" attrs="131">
-        <size>93</size>
+        <size>92</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Tester+&lt;InvokeMember_2&gt;c__AnonStorey2">
       <method name="Void &lt;&gt;m__0(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="131">
-        <size>110</size>
+        <size>109</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Tester+&lt;InvokeMember_6&gt;c__AnonStorey3">
       <method name="Void &lt;&gt;m__0(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="131">
-        <size>120</size>
+        <size>119</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Tester+&lt;SetIndex_3&gt;c__AnonStorey4">
       <method name="Void &lt;&gt;m__0(System.Dynamic.SetIndexBinder, System.Object[], System.Object)" attrs="131">
-        <size>120</size>
+        <size>119</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>67</size>
       </method>
       <method name="Void &lt;GetIndex_1&gt;m__25(System.Dynamic.GetIndexBinder, System.Object[])" attrs="145">
-        <size>93</size>
+        <size>92</size>
       </method>
       <method name="Void &lt;GetIndex_2&gt;m__26(System.Dynamic.GetIndexBinder, System.Object[])" attrs="145">
-        <size>112</size>
+        <size>111</size>
       </method>
       <method name="System.Object &lt;GetMember_1&gt;m__27(System.Dynamic.GetMemberBinder)" attrs="145">
         <size>75</size>
       </method>
       <method name="Void &lt;Invoke_1&gt;m__28(System.Dynamic.InvokeBinder, System.Object[])" attrs="145">
-        <size>102</size>
+        <size>101</size>
       </method>
       <method name="Void &lt;Invoke_2&gt;m__29(System.Dynamic.InvokeBinder, System.Object[])" attrs="145">
-        <size>74</size>
+        <size>72</size>
       </method>
       <method name="Void &lt;Invoke_4&gt;m__2A(System.Dynamic.InvokeBinder, System.Object[])" attrs="145">
         <size>128</size>
       </method>
       <method name="Void &lt;Invoke_5&gt;m__2B(System.Dynamic.InvokeBinder, System.Object[])" attrs="145">
-        <size>92</size>
+        <size>91</size>
       </method>
       <method name="Void &lt;Invoke_5&gt;m__2C(System.Object)" attrs="145">
         <size>94</size>
       </method>
       <method name="Void &lt;Invoke_6&gt;m__2D(System.Dynamic.InvokeBinder, System.Object[])" attrs="145">
-        <size>93</size>
+        <size>92</size>
       </method>
       <method name="Void &lt;InvokeMember_1&gt;m__2E(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="145">
-        <size>111</size>
+        <size>110</size>
       </method>
       <method name="Void &lt;InvokeMember_3&gt;m__2F(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="145">
-        <size>112</size>
+        <size>111</size>
       </method>
       <method name="Void &lt;InvokeMember_4&gt;m__30(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="145">
-        <size>111</size>
+        <size>110</size>
       </method>
       <method name="Void &lt;InvokeMember_7&gt;m__31(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="145">
-        <size>91</size>
+        <size>89</size>
       </method>
       <method name="Void &lt;InvokeMember_8&gt;m__32(System.Dynamic.InvokeMemberBinder, System.Object[])" attrs="145">
-        <size>112</size>
+        <size>111</size>
       </method>
       <method name="Void &lt;SetIndex_1&gt;m__33(System.Dynamic.SetIndexBinder, System.Object[], System.Object)" attrs="145">
-        <size>125</size>
+        <size>124</size>
       </method>
       <method name="Void &lt;SetIndex_2&gt;m__34(System.Dynamic.SetIndexBinder, System.Object[], System.Object)" attrs="145">
-        <size>140</size>
+        <size>139</size>
       </method>
       <method name="Void &lt;SetMember_1&gt;m__35(System.Dynamic.SetMemberBinder, System.Object)" attrs="145">
         <size>102</size>
   <test name="dtest-044.cs">
     <type name="C">
       <method name="Int32 Main()" attrs="150">
-        <size>868</size>
+        <size>867</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
       </method>
     </type>
   </test>
+  <test name="dtest-064.cs">
+    <type name="A">
+      <method name="Void .ctor(Action)" attrs="6278">
+        <size>8</size>
+      </method>
+    </type>
+    <type name="B">
+      <method name="System.Decimal Test(System.Object)" attrs="145">
+        <size>15</size>
+      </method>
+      <method name="Void &lt;B&gt;m__0()" attrs="145">
+        <size>113</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>37</size>
+      </method>
+    </type>
+    <type name="B2">
+      <method name="System.Decimal Test(System.Object)" attrs="145">
+        <size>15</size>
+      </method>
+      <method name="Void &lt;a&gt;m__0()" attrs="145">
+        <size>113</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>42</size>
+      </method>
+    </type>
+    <type name="M">
+      <method name="Void Main()" attrs="145">
+        <size>14</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
   <test name="dtest-anontype-01.cs">
     <type name="C">
       <method name="Void Main()" attrs="150">
         <size>2</size>
       </method>
       <method name="Void Main()" attrs="150">
-        <size>383</size>
+        <size>381</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>23</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>213</size>
+        <size>212</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>84</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
-        <size>20</size>
+        <size>19</size>
       </method>
       <method name="Void .ctor(E[])" attrs="6278">
         <size>15</size>
     </type>
     <type name="Crash">
       <method name="Void Main()" attrs="150">
-        <size>15</size>
+        <size>14</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Tests">
       <method name="Void Main()" attrs="150">
-        <size>22</size>
+        <size>21</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Tests">
       <method name="Void Main()" attrs="150">
-        <size>39</size>
+        <size>38</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="gtest-340.cs">
     <type name="Tests">
       <method name="T[] FindAll[T](T[], System.Predicate`1[T])" attrs="150">
-        <size>15</size>
+        <size>14</size>
       </method>
       <method name="Boolean ProtectedOnly(System.Reflection.MemberInfo)" attrs="129">
         <size>10</size>
         <size>16</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>25</size>
+        <size>24</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>2</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>189</size>
+        <size>187</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Base">
       <method name="System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()" attrs="481">
-        <size>20</size>
+        <size>19</size>
       </method>
     </type>
   </test>
         <size>10</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>51</size>
+        <size>50</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>25</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>27</size>
+        <size>26</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="gtest-495.cs">
     <type name="Repro">
       <method name="Void Main()" attrs="150">
-        <size>13</size>
+        <size>12</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>2</size>
       </method>
       <method name="Void Test()" attrs="134">
-        <size>38</size>
+        <size>37</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="C">
       <method name="Int32 Main()" attrs="150">
-        <size>80</size>
+        <size>78</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>2</size>
       </method>
       <method name="Void Main()" attrs="150">
-        <size>51</size>
+        <size>48</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="X2">
       <method name="Void Main()" attrs="150">
-        <size>24</size>
+        <size>22</size>
       </method>
       <method name="Void Foo[T1,T2](T2[])" attrs="145">
         <size>9</size>
         <size>42</size>
       </method>
       <method name="System.Linq.Expressions.Expression`1[System.Func`1[System.Func`1[System.Boolean]]] GetEvent()" attrs="134">
-        <size>41</size>
+        <size>40</size>
       </method>
       <method name="Void set_MyTypeProperty(MyType)" attrs="2182">
         <size>9</size>
         <size>244</size>
       </method>
       <method name="Void ArrayIndexTest_5()" attrs="129">
-        <size>109</size>
+        <size>108</size>
       </method>
       <method name="Void ArrayIndexTest_6()" attrs="129">
         <size>123</size>
       </method>
       <method name="Void ArrayIndexTest_7()" attrs="129">
-        <size>127</size>
+        <size>126</size>
       </method>
       <method name="Void ArrayLengthTest()" attrs="129">
-        <size>100</size>
+        <size>99</size>
       </method>
       <method name="Void ArrayLengthTest_2()" attrs="129">
         <size>92</size>
         <size>196</size>
       </method>
       <method name="Void CallTest_4()" attrs="129">
-        <size>110</size>
+        <size>108</size>
       </method>
       <method name="Void CallTest_5()" attrs="129">
         <size>100</size>
       </method>
       <method name="Void CallTest_6()" attrs="129">
-        <size>71</size>
+        <size>70</size>
       </method>
       <method name="Void CallTest_7()" attrs="129">
         <size>125</size>
         <size>184</size>
       </method>
       <method name="Void ConditionTest_5()" attrs="129">
-        <size>108</size>
+        <size>107</size>
       </method>
       <method name="Void ConstantTest()" attrs="129">
-        <size>60</size>
+        <size>59</size>
       </method>
       <method name="Void ConstantTest_2()" attrs="129">
-        <size>63</size>
+        <size>62</size>
       </method>
       <method name="Void ConstantTest_3()" attrs="129">
-        <size>55</size>
+        <size>54</size>
       </method>
       <method name="Void ConstantTest_4()" attrs="129">
-        <size>45</size>
+        <size>44</size>
       </method>
       <method name="Void ConstantTest_5()" attrs="129">
-        <size>60</size>
+        <size>59</size>
       </method>
       <method name="Void ConstantTest_6()" attrs="129">
-        <size>68</size>
+        <size>67</size>
       </method>
       <method name="Void ConstantTest_7()" attrs="129">
-        <size>63</size>
+        <size>62</size>
       </method>
       <method name="Void ConstantTest_8()" attrs="129">
-        <size>73</size>
+        <size>72</size>
       </method>
       <method name="Void ConstantTest_9()" attrs="129">
-        <size>73</size>
+        <size>72</size>
       </method>
       <method name="Void ConstantTest_10()" attrs="129">
-        <size>73</size>
+        <size>72</size>
       </method>
       <method name="Void ConstantTest_11()" attrs="129">
-        <size>60</size>
+        <size>59</size>
       </method>
       <method name="Void ConstantTest_13()" attrs="129">
-        <size>60</size>
+        <size>59</size>
       </method>
       <method name="Void ConstantTest_14()" attrs="129">
-        <size>73</size>
+        <size>72</size>
       </method>
       <method name="Void ConstantTest_15()" attrs="129">
-        <size>63</size>
+        <size>62</size>
       </method>
       <method name="Void ConvertTest()" attrs="129">
         <size>83</size>
         <size>119</size>
       </method>
       <method name="Void ConvertTest_9()" attrs="129">
-        <size>98</size>
+        <size>97</size>
       </method>
       <method name="Void ConvertTest_10()" attrs="129">
         <size>181</size>
         <size>102</size>
       </method>
       <method name="Void ConvertTest_12()" attrs="129">
-        <size>141</size>
+        <size>140</size>
       </method>
       <method name="Void ConvertTest_13()" attrs="129">
         <size>87</size>
         <size>170</size>
       </method>
       <method name="Void InvokeTest()" attrs="129">
-        <size>91</size>
+        <size>90</size>
       </method>
       <method name="Void InvokeTest_2()" attrs="129">
         <size>139</size>
       </method>
       <method name="Void LambdaTest()" attrs="129">
-        <size>90</size>
+        <size>89</size>
       </method>
       <method name="Void LeftShiftTest()" attrs="129">
         <size>156</size>
         <size>170</size>
       </method>
       <method name="Void ListInitTest()" attrs="129">
-        <size>405</size>
+        <size>404</size>
       </method>
       <method name="Void ListInitTest_2()" attrs="129">
         <size>293</size>
       </method>
       <method name="Void MemberAccessTest()" attrs="129">
-        <size>133</size>
+        <size>132</size>
       </method>
       <method name="Void MemberAccessTest_2()" attrs="129">
-        <size>64</size>
+        <size>63</size>
       </method>
       <method name="Void MemberAccessTest_3()" attrs="129">
-        <size>114</size>
+        <size>113</size>
       </method>
       <method name="Void MemberAccessTest_4()" attrs="129">
-        <size>92</size>
+        <size>91</size>
       </method>
       <method name="Void MemberAccessTest_5()" attrs="129">
         <size>40</size>
       </method>
       <method name="Void MemberAccessTest_6()" attrs="129">
-        <size>105</size>
+        <size>104</size>
       </method>
       <method name="Void MemberAccessTest_7()" attrs="129">
         <size>110</size>
       </method>
       <method name="Void MemberAccessTest_8()" attrs="129">
-        <size>64</size>
+        <size>63</size>
       </method>
       <method name="Void MemberAccessTest_9()" attrs="129">
-        <size>92</size>
+        <size>91</size>
       </method>
       <method name="Void MemberInitTest()" attrs="129">
-        <size>303</size>
+        <size>302</size>
       </method>
       <method name="Void MemberInitTest_2()" attrs="129">
-        <size>251</size>
+        <size>250</size>
       </method>
       <method name="Void MemberInitTest_3()" attrs="129">
         <size>125</size>
       </method>
       <method name="Void MemberInitTest_4()" attrs="129">
-        <size>67</size>
+        <size>65</size>
       </method>
       <method name="Void MemberInitTest_5()" attrs="129">
-        <size>119</size>
+        <size>117</size>
       </method>
       <method name="Void ModuloTest()" attrs="129">
         <size>101</size>
         <size>89</size>
       </method>
       <method name="Void NewArrayInitTest()" attrs="129">
-        <size>93</size>
+        <size>92</size>
       </method>
       <method name="Void NewArrayInitTest_2()" attrs="129">
-        <size>65</size>
+        <size>62</size>
       </method>
       <method name="Void NewArrayInitTest_3()" attrs="129">
         <size>137</size>
       </method>
       <method name="Void NewArrayInitTest_4()" attrs="129">
-        <size>121</size>
+        <size>120</size>
       </method>
       <method name="Void NewArrayInitTest_5()" attrs="129">
-        <size>159</size>
+        <size>158</size>
       </method>
       <method name="Void NewArrayInitTest_6()" attrs="129">
-        <size>104</size>
+        <size>103</size>
       </method>
       <method name="Void NewArrayBoundsTest()" attrs="129">
-        <size>124</size>
+        <size>123</size>
       </method>
       <method name="Void NewArrayBoundsTest_2()" attrs="129">
-        <size>124</size>
+        <size>123</size>
       </method>
       <method name="Void NewArrayBoundsTest_3()" attrs="129">
-        <size>86</size>
+        <size>85</size>
       </method>
       <method name="Void NewArrayBoundsTest_4()" attrs="129">
-        <size>83</size>
+        <size>82</size>
       </method>
       <method name="Void NewTest()" attrs="129">
-        <size>94</size>
+        <size>93</size>
       </method>
       <method name="Void NewTest_2()" attrs="129">
-        <size>62</size>
+        <size>61</size>
       </method>
       <method name="Void NewTest_3()" attrs="129">
-        <size>99</size>
+        <size>98</size>
       </method>
       <method name="Void NewTest_4()" attrs="129">
         <size>253</size>
       </method>
       <method name="Void NewTest_5()" attrs="129">
-        <size>376</size>
+        <size>375</size>
       </method>
       <method name="Void NewTest_6()" attrs="129">
-        <size>183</size>
+        <size>182</size>
       </method>
       <method name="Void NewTest_7()" attrs="129">
-        <size>54</size>
+        <size>53</size>
       </method>
       <method name="Void NotTest()" attrs="129">
         <size>71</size>
         <size>74</size>
       </method>
       <method name="Void ParameterTest_2()" attrs="129">
-        <size>76</size>
+        <size>74</size>
       </method>
       <method name="Void ParameterTest_3()" attrs="129">
         <size>74</size>
         <size>101</size>
       </method>
       <method name="Void QuoteTest()" attrs="129">
-        <size>86</size>
+        <size>84</size>
       </method>
       <method name="Void QuoteTest_2()" attrs="129">
-        <size>100</size>
+        <size>99</size>
       </method>
       <method name="Void RightShiftTest()" attrs="129">
         <size>153</size>
         <size>81</size>
       </method>
       <method name="Void TypeIsTest_5()" attrs="129">
-        <size>75</size>
+        <size>74</size>
       </method>
       <method name="Void TypeIsTest_6()" attrs="129">
         <size>112</size>
         <size>12</size>
       </method>
       <method name="Void NewTest_8()" attrs="129">
-        <size>64</size>
+        <size>63</size>
       </method>
       <method name="Void CallTest_10()" attrs="129">
-        <size>137</size>
+        <size>136</size>
       </method>
     </type>
   </test>
         <size>2</size>
       </method>
       <method name="System.String Param(System.String)" attrs="145">
-        <size>122</size>
+        <size>121</size>
       </method>
       <method name="Int32 Main()" attrs="150">
         <size>173</size>
     </type>
     <type name="C">
       <method name="Int32 Main()" attrs="150">
-        <size>495</size>
+        <size>490</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>48</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>358</size>
+        <size>357</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="gtest-etree-06.cs">
     <type name="Test">
       <method name="Int32 Main()" attrs="150">
-        <size>53</size>
+        <size>52</size>
       </method>
       <method name="Int32 Value()" attrs="145">
         <size>10</size>
         <size>2</size>
       </method>
       <method name="Int32 TestInstance()" attrs="129">
-        <size>337</size>
+        <size>336</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>580</size>
+        <size>577</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>11</size>
       </method>
       <method name="Int32 Goo(Boolean)" attrs="134">
-        <size>231</size>
+        <size>228</size>
       </method>
       <method name="Int32 Main()" attrs="150">
         <size>22</size>
   <test name="gtest-etree-09.cs">
     <type name="Mono.C">
       <method name="Int32 Main()" attrs="150">
-        <size>296</size>
+        <size>294</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Foo`1[T]">
       <method name="Boolean ContainsAll[U](System.Collections.Generic.IEnumerable`1[U])" attrs="134">
-        <size>200</size>
+        <size>199</size>
       </method>
     </type>
   </test>
     </type>
     <type name="Test">
       <method name="Void Invalid(Int32)" attrs="134">
-        <size>125</size>
+        <size>124</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>19</size>
       </method>
       <method name="Boolean MoveNext()" attrs="486">
-        <size>148</size>
+        <size>147</size>
       </method>
       <method name="Void Dispose()" attrs="486">
         <size>15</size>
         <size>33</size>
       </method>
       <method name="T Value[T]()" attrs="145">
-        <size>86</size>
+        <size>85</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="FieldInfoBug.GenericClass`1[T]">
       <method name="Void .ctor(String)" attrs="6278">
-        <size>59</size>
+        <size>58</size>
       </method>
     </type>
     <type name="FieldInfoBug.GenericClass`1+&lt;GenericClass&gt;c__AnonStorey0[T]">
     </type>
     <type name="NotifyingPropertyTest">
       <method name="Void CreateDependent_NotifierNull()" attrs="134">
-        <size>59</size>
+        <size>57</size>
       </method>
       <method name="Void CreateDependent_DependentsNull()" attrs="134">
-        <size>84</size>
+        <size>83</size>
       </method>
       <method name="Void Main()" attrs="150">
         <size>2</size>
     </type>
     <type name="A`1+B`1[TA,TB]">
       <method name="Void foo()" attrs="150">
-        <size>40</size>
+        <size>39</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>8</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>1210</size>
+        <size>1204</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>19</size>
   <test name="gtest-etree-28.cs">
     <type name="Repro">
       <method name="Void UseField()" attrs="129">
-        <size>70</size>
+        <size>69</size>
       </method>
       <method name="Void TakeExpression(System.Linq.Expressions.Expression`1[System.Action])" attrs="129">
         <size>2</size>
   <test name="gtest-exmethod-20.cs">
     <type name="Outer.Inner.Test">
       <method name="Void M(I)" attrs="145">
-        <size>14</size>
+        <size>13</size>
       </method>
       <method name="Void Main()" attrs="150">
         <size>2</size>
   <test name="gtest-exmethod-27.cs">
     <type name="Bar.Program">
       <method name="Void Main()" attrs="150">
-        <size>18</size>
+        <size>17</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="A">
       <method name="Void Main()" attrs="150">
-        <size>13</size>
+        <size>12</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>23</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>88</size>
+        <size>87</size>
       </method>
       <method name="Boolean Foo(Int32[])" attrs="145">
         <size>52</size>
   <test name="gtest-friend-14.cs">
     <type name="Test">
       <method name="Int32 Main()" attrs="150">
-        <size>21</size>
+        <size>20</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="C`1[T]">
       <method name="System.Collections.IEnumerator GetEnumerator()" attrs="134">
-        <size>20</size>
+        <size>19</size>
       </method>
     </type>
     <type name="C`1+&lt;Filter&gt;c__Iterator0[T]">
         <size>10</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>53</size>
+        <size>52</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="gtest-linq-01.cs">
     <type name="from.C">
       <method name="Void Main()" attrs="150">
-        <size>2181</size>
+        <size>2179</size>
       </method>
       <method name="Void Foo(Int32, Boolean)" attrs="129">
         <size>16</size>
     </type>
     <type name="NameCollisionTest.C">
       <method name="Void Main()" attrs="150">
-        <size>79</size>
+        <size>78</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="C">
       <method name="Void &lt;Main&gt;m__0()" attrs="145">
-        <size>162</size>
+        <size>159</size>
       </method>
       <method name="System.Collections.Generic.IEnumerable`1[B] &lt;Main&gt;m__1(A)" attrs="145">
-        <size>15</size>
+        <size>14</size>
       </method>
       <method name="&lt;&gt;__AnonType0`2[A,B] &lt;Main&gt;m__2(A, B)" attrs="145">
         <size>16</size>
         <size>10</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>192</size>
+        <size>190</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>10</size>
       </method>
       <method name="Int32 Main()" attrs="145">
-        <size>42</size>
+        <size>41</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
       </method>
     </type>
   </test>
+  <test name="gtest-optional-36.cs">
+    <type name="Program">
+      <method name="Int32 Arg(UInt32, Int64)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Arg(Int32, UInt64, Int32)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Arg_2(UInt32, Int64, Int32[])" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Arg_2(Int32, UInt64, Int32)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Arg_3(Int32, Int64, Int32[])" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Arg_3(UInt32, UInt64, Int32, Int32, Int32[])" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Main()" attrs="150">
+        <size>237</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
+  <test name="gtest-optional-37.cs">
+    <type name="Test1">
+      <method name="System.Object Foo(Int32, Int32)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="System.Object Foo(System.Object, System.Object)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Void Main()" attrs="150">
+        <size>32</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
   <test name="gtest-partial-01.cs">
     <type name="B`1[U]">
       <method name="Void .ctor()" attrs="6278">
   <test name="gtest-variance-13.cs">
     <type name="A">
       <method name="Void Test()" attrs="150">
-        <size>18</size>
+        <size>17</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="gtest-variance-19.cs">
     <type name="Test">
       <method name="Void Bla[T,U]()" attrs="145">
-        <size>13</size>
+        <size>12</size>
       </method>
       <method name="Void Main()" attrs="150">
         <size>7</size>
         <size>9</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>94</size>
+        <size>93</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="test-232.cs">
     <type name="CtorInfoTest">
       <method name="Void Main(System.String[])" attrs="150">
-        <size>978</size>
+        <size>977</size>
       </method>
       <method name="Void Assert(System.Object, System.Object)" attrs="145">
         <size>43</size>
     </type>
     <type name="UnsupportedClassVersionError">
       <method name="Void .ctor(String)" attrs="6275">
-        <size>15</size>
+        <size>14</size>
       </method>
     </type>
   </test>
     </type>
     <type name="ChildClass">
       <method name="Void .ctor()" attrs="6278">
-        <size>13</size>
+        <size>12</size>
       </method>
     </type>
     <type name="M">
         <size>2</size>
       </method>
       <method name="Void Main()" attrs="150">
-        <size>243</size>
+        <size>242</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="SimpleAttribute">
       <method name="Int64[] get_ArrayValue()" attrs="2182">
-        <size>15</size>
+        <size>14</size>
       </method>
       <method name="Void set_ArrayValue(Int64[])" attrs="2182">
         <size>2</size>
     </type>
     <type name="X+Derived+Nested">
       <method name="Void G()" attrs="134">
-        <size>22</size>
+        <size>21</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>41</size>
       </method>
       <method name="Void Main(System.String[])" attrs="150">
-        <size>259</size>
+        <size>257</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>60</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>165</size>
+        <size>164</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
   <test name="test-772.cs">
     <type name="Test">
       <method name="Void Main()" attrs="150">
-        <size>15</size>
+        <size>14</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>7</size>
       </method>
       <method name="System.Collections.IEnumerator System.Collections.IEnumerable.GetEnumerator()" attrs="481">
-        <size>20</size>
+        <size>19</size>
       </method>
     </type>
   </test>
         <size>12</size>
       </method>
       <method name="Void TestCallOnly()" attrs="129">
-        <size>66</size>
+        <size>65</size>
       </method>
       <method name="Void SomeMethod()" attrs="486">
         <size>2</size>
   <test name="test-850.cs">
     <type name="C">
       <method name="Int32 Main()" attrs="150">
-        <size>39</size>
+        <size>38</size>
       </method>
       <method name="Int32 F(System.String, System.String[])" attrs="145">
         <size>10</size>
         <size>20</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>71</size>
+        <size>70</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>2</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>288</size>
+        <size>284</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
       </method>
     </type>
   </test>
+  <test name="test-933.cs">
+    <type name="X">
+      <method name="Int32 Foo(X[])" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Foo(System.Object)" attrs="145">
+        <size>10</size>
+      </method>
+      <method name="Int32 Main()" attrs="145">
+        <size>29</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
+  <test name="test-934.cs">
+    <type name="X">
+      <method name="Int32 Main()" attrs="150">
+        <size>106</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
   <test name="test-94.cs">
     <type name="Base">
       <method name="Int32 IVehicle.Start()" attrs="481">
         <size>10</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>95</size>
+        <size>94</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="Foo`1+&lt;ContainsAll&gt;c__AnonStorey0`1[T,U]">
       <method name="Boolean &lt;&gt;m__0()" attrs="131">
-        <size>210</size>
+        <size>209</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="AwaitNS.MemberAccess">
       <method name="Void M()" attrs="145">
-        <size>13</size>
+        <size>12</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
     </type>
     <type name="O">
       <method name="Void Main()" attrs="150">
-        <size>23</size>
+        <size>22</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
       </method>
     </type>
   </test>
+  <test name="test-async-85.cs">
+    <type name="Program">
+      <method name="Int32 Main()" attrs="145">
+        <size>197</size>
+      </method>
+      <method name="System.Threading.Tasks.Task Test(Boolean)" attrs="145">
+        <size>41</size>
+      </method>
+      <method name="System.Threading.Tasks.Task Test2(Boolean)" attrs="145">
+        <size>41</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+    <type name="Program+&lt;Test&gt;c__async0">
+      <method name="Void MoveNext()" attrs="486">
+        <size>543</size>
+      </method>
+      <method name="Void SetStateMachine(System.Runtime.CompilerServices.IAsyncStateMachine)" attrs="486">
+        <size>13</size>
+      </method>
+    </type>
+    <type name="Program+&lt;Test2&gt;c__async1">
+      <method name="Void MoveNext()" attrs="486">
+        <size>398</size>
+      </method>
+      <method name="Void SetStateMachine(System.Runtime.CompilerServices.IAsyncStateMachine)" attrs="486">
+        <size>13</size>
+      </method>
+    </type>
+  </test>
   <test name="test-cls-00.cs">
     <type name="CLSCLass_6">
       <method name="Void add_Disposed(Delegate)" attrs="2182">
         <size>76</size>
       </method>
       <method name="Void Test_2()" attrs="129">
-        <size>51</size>
+        <size>49</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>40</size>
       </method>
       <method name="Int32 Main()" attrs="150">
-        <size>213</size>
+        <size>244</size>
       </method>
       <method name="Void .ctor()" attrs="6278">
         <size>7</size>
         <size>7</size>
       </method>
     </type>
+    <type name="MainClass">
+      <method name="Void ParameterTest(Person)" attrs="129">
+        <size>12</size>
+      </method>
+    </type>
   </test>
   <test name="test-null-operator-01.cs">
     <type name="S">
         <size>477</size>
       </method>
       <method name="Int32 TestReferenceType()" attrs="145">
-        <size>229</size>
+        <size>227</size>
       </method>
       <method name="Int32 TestGeneric[T](T)" attrs="145">
         <size>118</size>
       </method>
     </type>
   </test>
+  <test name="test-null-operator-04.cs">
+    <type name="C1">
+      <method name="Void Foo[T](IFoo`1[T])" attrs="134">
+        <size>38</size>
+      </method>
+      <method name="Void Foo2[T](IFoo`1[T])" attrs="134">
+        <size>17</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+    <type name="C2`1[T]">
+      <method name="Void Foo()" attrs="134">
+        <size>33</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+    <type name="Program">
+      <method name="Void Test[T](System.Func`1[T])" attrs="145">
+        <size>31</size>
+      </method>
+      <method name="Void Test2[T](System.Func`1[T])" attrs="145">
+        <size>17</size>
+      </method>
+      <method name="Void Main()" attrs="145">
+        <size>102</size>
+      </method>
+      <method name="Int32 &lt;Main&gt;m__0()" attrs="145">
+        <size>9</size>
+      </method>
+      <method name="Int32 &lt;Main&gt;m__1()" attrs="145">
+        <size>9</size>
+      </method>
+      <method name="Void .ctor()" attrs="6278">
+        <size>7</size>
+      </method>
+    </type>
+  </test>
   <test name="test-null-operator-05.cs">
     <type name="CI">
       <method name="Void set_Item(System.String, System.String)" attrs="2182">
index 418bcdd85f5cfaa1b52bb9af6ade6a8739bbe0b2..693318cbea7e07fdb27df8413379a15d159e7ac0 100644 (file)
@@ -16,6 +16,7 @@ net_4_5_dirs := \
        xbuild          \
        csharp          \
        corcompare      \
+       mono-api-html \
        compiler-tester \
        mono-xmltool    \
        mono-shlib-cop  \
@@ -48,7 +49,7 @@ net_4_5_dirs := \
        mono-symbolicate        \
        linker-analyzer
 
-build_SUBDIRS = gacutil security culevel cil-stringreplacer
+build_SUBDIRS = gacutil security culevel cil-stringreplacer commoncryptogenerator
 net_4_5_SUBDIRS = gacutil
 net_4_5_PARALLEL_SUBDIRS = $(net_4_5_dirs)
 
index caf1a67a5b2a322c1a2020f6dbcec1b674f9e242..bdc741144ea595cb7d7bcbeb8b509e5a3e225148 100644 (file)
@@ -12,6 +12,7 @@ using System;
 using System.Globalization;
 using System.IO;
 using System.Collections;
+using System.Collections.Generic;
 using System.Reflection;
 using System.Reflection.Emit;
 using System.Security.Cryptography;
@@ -19,6 +20,7 @@ using System.Text;
 using System.Configuration.Assemblies;
 
 using Mono.Security.Cryptography;
+using IKR = IKVM.Reflection;
 
 namespace Mono.AssemblyLinker
 {
@@ -591,46 +593,8 @@ namespace Mono.AssemblyLinker
                         * Emit Manifest
                         * */
 
-                       if (isTemplateFile) {
-                               // LAMESPEC: according to MSDN, the template assembly must have a
-                               // strong name but this is not enforced
-                               Assembly assembly = Assembly.LoadFrom (templateFile);
-
-                               // inherit signing related settings from template, but do not
-                               // override command-line options
-                               object [] attrs = assembly.GetCustomAttributes (true);
-                               foreach (object o in attrs) {
-                                       if (o is AssemblyKeyFileAttribute) {
-                                               if (keyfile != null)
-                                                       // ignore if specified on command line
-                                                       continue;
-                                               AssemblyKeyFileAttribute keyFileAttr = (AssemblyKeyFileAttribute) o;
-                                               // ignore null or zero-length keyfile
-                                               if (keyFileAttr.KeyFile == null || keyFileAttr.KeyFile.Length == 0)
-                                                       continue;
-                                               keyfile = Path.Combine (Path.GetDirectoryName(templateFile),
-                                                       keyFileAttr.KeyFile);
-                                       } else if (o is AssemblyDelaySignAttribute) {
-                                               if (delaysign != DelaySign.NotSet)
-                                                       // ignore if specified on command line
-                                                       continue;
-                                               AssemblyDelaySignAttribute delaySignAttr = (AssemblyDelaySignAttribute) o;
-                                               delaysign = delaySignAttr.DelaySign ? DelaySign.Yes :
-                                                       DelaySign.No;
-                                       } else if (o is AssemblyKeyNameAttribute) {
-                                               if (keyname != null)
-                                                       // ignore if specified on command line
-                                                       continue;
-                                               AssemblyKeyNameAttribute keynameAttr = (AssemblyKeyNameAttribute) o;
-                                               // ignore null or zero-length keyname
-                                               if (keynameAttr.KeyName == null || keynameAttr.KeyName.Length == 0)
-                                                       continue;
-                                               keyname = keynameAttr.KeyName;
-                                       }
-                               }
-                               aname.Version = assembly.GetName().Version;
-                               aname.HashAlgorithm = assembly.GetName().HashAlgorithm;
-                       }
+                       if (isTemplateFile)
+                               aname = ReadCustomAttributesFromTemplateFile (templateFile, aname);
 
                        SetKeyPair (aname);
 
@@ -765,6 +729,85 @@ namespace Mono.AssemblyLinker
                        }
                }
 
+               private AssemblyName ReadCustomAttributesFromTemplateFile (string templateFile, AssemblyName aname)
+               {
+                       // LAMESPEC: according to MSDN, the template assembly must have a
+                       // strong name but this is not enforced
+                       const IKR.UniverseOptions options = IKR.UniverseOptions.MetadataOnly;
+
+                       var universe = new IKR.Universe (options);
+                       var asm = universe.LoadFile (templateFile);
+
+                       // Create missing assemblies, we don't want to load them!
+                       // Code taken from ikdasm
+                       var names = new HashSet<string> ();
+                       IKR.AssemblyName[] assembly_refs = asm.ManifestModule.__GetReferencedAssemblies ();
+
+                       var resolved_assemblies = new IKR.Assembly [assembly_refs.Length];
+                       for (int i = 0; i < resolved_assemblies.Length; i++) {
+                               string name = assembly_refs [i].Name;
+
+                               while (names.Contains (name)) {
+                                       name = name + "_" + i;
+                               }
+                               names.Add (name);
+                               resolved_assemblies [i] = universe.CreateMissingAssembly (assembly_refs [i].FullName);
+                       }
+                       asm.ManifestModule.__ResolveReferencedAssemblies (resolved_assemblies);
+
+                       foreach (var attr_data in asm.__GetCustomAttributes (null, false)) {
+                               string asm_name = attr_data.AttributeType.Assembly.GetName ().Name;
+                               if (asm_name != "mscorlib")
+                                       continue;
+
+                               switch (attr_data.AttributeType.FullName) {
+                                       case "System.Reflection.AssemblyKeyFileAttribute": {
+                                               if (keyfile != null)
+                                                       // ignore if specified on command line
+                                                       continue;
+
+                                               // / AssemblyKeyFileAttribute .ctor(string keyFile)
+                                               string key_file_value = (string) attr_data.ConstructorArguments [0].Value;
+
+                                               if (!String.IsNullOrEmpty (key_file_value))
+                                                       keyfile = Path.Combine (Path.GetDirectoryName (templateFile), key_file_value);
+                                       }
+                                       break;
+
+                                       case "System.Reflection.AssemblyDelaySignAttribute": {
+                                               if (delaysign != DelaySign.NotSet)
+                                                       // ignore if specified on command line
+                                                       continue;
+
+                                               // AssemblyDelaySignAttribute .ctor(bool delaySign)
+                                               bool delay_sign_value = (bool) attr_data.ConstructorArguments [0].Value;
+                                               delaysign = delay_sign_value ? DelaySign.Yes : DelaySign.No;
+                                       }
+                                       break;
+
+                                       case "System.Reflection.AssemblyKeyNameAttribute": {
+                                               if (keyname != null)
+                                                       // ignore if specified on command line
+                                                       continue;
+
+                                               // AssemblyKeyNameAttribute .ctor(string keyName)
+                                               string key_name_value = (string) attr_data.ConstructorArguments [0].Value;
+
+                                               // ignore null or zero-length keyname
+                                               if (!String.IsNullOrEmpty (key_name_value))
+                                                       keyname = key_name_value;
+                                       }
+                                       break;
+                               }
+                       }
+
+                       var asm_name_for_template_file = asm.GetName ();
+                       aname.Version = asm_name_for_template_file.Version;
+                       aname.HashAlgorithm = asm_name_for_template_file.HashAlgorithm;
+
+                       return aname;
+               }
+
                private void LoadArgs (string file, ArrayList args) {
                        StreamReader f = null;
                        string line;
index a4505c123f5ab7a5fbfc8cbafa8b04c0ada6ca66..d2cea54c02e12c544c56576c93308018b211d71a 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/al
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:Mono.Security.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System System.Core Mono.Security System.Security Mono.CompilerServices.SymbolWriter
 PROGRAM = al.exe
 
 CLEAN_FILES = al.exe al.exe.mdb
index 08f674c872a3517204d766c24283477200aa0991..96d3be17ba56dbd1414eefabea4bb4a5704559b1 100644 (file)
@@ -1,2 +1,9 @@
 Al.cs
 ../../build/common/Consts.cs
+../../../external/ikvm/reflect/*.cs
+../../../external/ikvm/reflect/Emit/*.cs
+../../../external/ikvm/reflect/Metadata/*.cs
+../../../external/ikvm/reflect/Reader/*.cs
+../../../external/ikvm/reflect/Writer/*.cs
+../../../external/ikvm/reflect/Impl/*.cs
+../../../external/ikvm/reflect/Properties/*.cs
index a39c748e5e6c5c9d0b017ff1980db73c1c0935b8..6d2df98702dc1a8030bf2d02651524743aa5caca 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/browsercaps-updater
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System
 
 PROGRAM = browsercaps-updater.exe
 
index 71935aebb6c5735e4dda47ec573e79eca95cc532..52d624ffed493aae6de62feccda36aec2f1f089f 100644 (file)
@@ -4,6 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = cccheck.exe
 
-LOCAL_MCS_FLAGS = -r:Mono.CodeContracts.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = Mono.CodeContracts System
 
 include ../../build/executable.make
index bac67d3de8ae52278bef66d29f67091d394c902c..00e711b27953e86b2fcab9f4ae4ef2d55bbc067e 100644 (file)
@@ -4,6 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = ccrewrite.exe
 
-LOCAL_MCS_FLAGS = -r:Mono.CodeContracts.dll -r:System.dll -r:System.Core.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = Mono.CodeContracts System System.Core
 
 include ../../build/executable.make
index 93153cb19b9dbcd34613f62ff8565663e92e37e8..a6708e2d371e1245bcce89b70772e3ff57ebf7ae 100644 (file)
@@ -5,6 +5,6 @@ include ../../build/rules.make
 PROGRAM = cil-stringreplacer.exe
 NO_INSTALL = yes
 
-LOCAL_MCS_FLAGS = -r:System.dll
+LIB_REFS = System Mono.Cecil
 
 include ../../build/executable.make
index f86922be2bf58e3560dcd3e318ec0d80a0d2f2a1..2414206c692ef2023b30b34d7ca16ebceebc8306 100644 (file)
@@ -100,7 +100,8 @@ public class Program
 
        static void RewriteAssembly (string assemblyLocation, Dictionary<string, string> resourcesStrings, CmdOptions options)
        {
-               var assembly = AssemblyDefinition.ReadAssembly (assemblyLocation);
+               var readerParameters = new ReaderParameters { ReadSymbols = true };
+               var assembly = AssemblyDefinition.ReadAssembly (assemblyLocation, readerParameters);
                foreach (var module in assembly.Modules) {
                        foreach (var type in module.GetTypes ()) {
                                foreach (var method in type.Methods) {
@@ -124,7 +125,8 @@ public class Program
                        }
                }
 
-               assembly.Write (assemblyLocation);
+               var writerParameters = new WriterParameters { WriteSymbols = true };
+               assembly.Write (assemblyLocation, writerParameters);
        }
 
        static bool LoadGetResourceStrings (Dictionary<string, string> resourcesStrings, CmdOptions options)
diff --git a/mcs/tools/cil-stringreplacer/cil-stringreplacer.csproj b/mcs/tools/cil-stringreplacer/cil-stringreplacer.csproj
new file mode 100644 (file)
index 0000000..230cd62
--- /dev/null
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="utf-8"?>\r
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
+  <PropertyGroup>\r
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>\r
+    <Platform Condition=" '$(Platform)' == '' ">x86</Platform>\r
+    <ProjectGuid>{7A08A2B6-5AC3-4268-8566-B07648B50D01}</ProjectGuid>\r
+    <OutputType>Exe</OutputType>\r
+    <RootNamespace>cilstringreplacer</RootNamespace>\r
+    <AssemblyName>cilstringreplacer</AssemblyName>\r
+    <TargetFrameworkVersion>v4.6</TargetFrameworkVersion>\r
+  </PropertyGroup>\r
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|x86' ">\r
+    <DebugSymbols>true</DebugSymbols>\r
+    <DebugType>full</DebugType>\r
+    <Optimize>false</Optimize>\r
+    <OutputPath>bin\Debug</OutputPath>\r
+    <DefineConstants>DEBUG;</DefineConstants>\r
+    <ErrorReport>prompt</ErrorReport>\r
+    <WarningLevel>4</WarningLevel>\r
+    <ExternalConsole>false</ExternalConsole>\r
+    <PlatformTarget>x86</PlatformTarget>\r
+    <Commandlineparameters>--resourcestrings:/Users/marek/git/mono/external/referencesource/mscorlib/mscorlib.txt /Users/marek/git/mono/mcs/class/lib/net_4_x/mscorlib.dll</Commandlineparameters>\r
+    <ConsolePause>false</ConsolePause>\r
+  </PropertyGroup>\r
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|x86' ">\r
+    <Optimize>true</Optimize>\r
+    <OutputPath>bin\Release</OutputPath>\r
+    <ErrorReport>prompt</ErrorReport>\r
+    <WarningLevel>4</WarningLevel>\r
+    <ExternalConsole>true</ExternalConsole>\r
+    <PlatformTarget>x86</PlatformTarget>\r
+  </PropertyGroup>\r
+  <ItemGroup>\r
+    <Reference Include="System" />\r
+    <Reference Include="Mono.Cecil">\r
+      <HintPath>..\..\class\lib\net_4_x\Mono.Cecil.dll</HintPath>\r
+    </Reference>\r
+  </ItemGroup>\r
+  <ItemGroup>\r
+    <Compile Include="cil-stringreplacer.cs">\r
+      <Link>cil-stringreplacer.cs</Link>\r
+    </Compile>\r
+    <Compile Include="..\..\class\Mono.Options\Mono.Options\Options.cs">\r
+      <Link>Options.cs</Link>\r
+    </Compile>\r
+  </ItemGroup>\r
+  <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />\r
+</Project>
\ No newline at end of file
index 90536b886aa757b695ba77603c6a0efb5eb912b7..c16659f2b39c76efd24a0756765ea42799ef42b1 100644 (file)
@@ -1,9 +1,2 @@
 cil-stringreplacer.cs
 ../../class/Mono.Options/Mono.Options/Options.cs
-../../../external/cecil/Mono.Cecil/*.cs
-../../../external/cecil/Mono.Cecil.Cil/*.cs
-../../../external/cecil/Mono.Cecil.Metadata/*.cs
-../../../external/cecil/Mono.Cecil.PE/*.cs
-../../../external/cecil/Mono.Collections.Generic/*.cs
-../../../external/cecil/Mono/Empty.cs
-../../../external/cecil/Mono.Security.Cryptography/*.cs
index 6c3154589a67f21cc0866e0ad37de1cc393e7ef0..e84d78325e6b1cb4efd81b13174b37445881aa51 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/cil-strip
 SUBDIRS =
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System
 
 PROGRAM = mono-cil-strip.exe
 
diff --git a/mcs/tools/commoncryptogenerator/CommonCryptorGenerator.cs b/mcs/tools/commoncryptogenerator/CommonCryptorGenerator.cs
new file mode 100644 (file)
index 0000000..f177c17
--- /dev/null
@@ -0,0 +1,104 @@
+//
+// CommonCrypto code generator for symmetric block cipher algorithms
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012 Xamarin Inc.
+//
+
+using System;
+using System.IO;
+
+namespace Xamarin {
+
+       public static class CommonCryptor {
+               
+               static public void Generate (string namespaceName, string typeName, string baseTypeName, string ccAlgorithmName, string feedbackSize = "8", string ctorInitializers = null)
+               {
+                       string template = @"// Generated file to bind CommonCrypto cipher algorithms - DO NOT EDIT
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012-2014 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+
+using Mono.Security.Cryptography;
+using Crimson.CommonCrypto;
+
+namespace %NAMESPACE% {
+
+       public sealed partial class %TYPE% : %BASE% {
+               
+               public %TYPE% ()
+               {
+                       FeedbackSizeValue = %FEEDBACKSIZE%;
+                       %CTOR_INIT%
+               }
+               
+               public override void GenerateIV ()
+               {
+                       IVValue = KeyBuilder.IV (BlockSizeValue >> 3);
+               }
+               
+               public override void GenerateKey ()
+               {
+                       KeyValue = KeyBuilder.Key (KeySizeValue >> 3);
+               }
+               
+               public override ICryptoTransform CreateDecryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       IntPtr decryptor = IntPtr.Zero;
+                       switch (Mode) {
+                       case CipherMode.CBC:
+                               decryptor = Cryptor.Create (CCOperation.Decrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.None, rgbKey, rgbIV);
+                               return new FastCryptorTransform (decryptor, this, false, rgbIV);
+                       case CipherMode.ECB:
+                               decryptor = Cryptor.Create (CCOperation.Decrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.ECBMode, rgbKey, rgbIV);
+                               return new FastCryptorTransform (decryptor, this, false, rgbIV);
+                       case CipherMode.CFB:
+#if MONOTOUCH || XAMMAC
+                               IntPtr encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.ECBMode, rgbKey, rgbIV);
+                               decryptor = Cryptor.Create (CCOperation.Decrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.ECBMode, rgbKey, rgbIV);
+                               return new CryptorTransform (decryptor, encryptor, this, false, rgbIV);
+#else
+                               throw new CryptographicException (""CFB is not supported by Crimson.CommonCrypto"");
+#endif
+                       default:
+                               throw new CryptographicException (String.Format (""{0} is not supported by the .NET framework"", Mode));
+                       }
+               }
+               
+               public override ICryptoTransform CreateEncryptor (byte[] rgbKey, byte[] rgbIV) 
+               {
+                       IntPtr encryptor = IntPtr.Zero;
+                       switch (Mode) {
+                       case CipherMode.CBC:
+                               encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.None, rgbKey, rgbIV);
+                               return new FastCryptorTransform (encryptor, this, true, rgbIV);
+                       case CipherMode.ECB:
+                               encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.ECBMode, rgbKey, rgbIV);
+                               return new FastCryptorTransform (encryptor, this, true, rgbIV);
+                       case CipherMode.CFB:
+#if MONOTOUCH || XAMMAC
+                               encryptor = Cryptor.Create (CCOperation.Encrypt, CCAlgorithm.%CCALGORITHM%, CCOptions.ECBMode, rgbKey, rgbIV);
+                               return new CryptorTransform (encryptor, IntPtr.Zero, this, true, rgbIV);
+#else
+                               throw new CryptographicException (""CFB is not supported by Crimson.CommonCrypto"");
+#endif
+                       default:
+                               throw new CryptographicException (String.Format (""{0} is not supported by the .NET framework"", Mode));
+                       }
+               }
+       }
+}";
+                       
+                       File.WriteAllText (typeName + ".g.cs", template.Replace ("%NAMESPACE%", namespaceName).
+                               Replace ("%TYPE%", typeName).Replace ("%BASE%", baseTypeName).Replace("%FEEDBACKSIZE%", feedbackSize).Replace ("%CTOR_INIT%", ctorInitializers).
+                               Replace ("%CCALGORITHM%", ccAlgorithmName.ToString ()));
+               }
+       }
+}
diff --git a/mcs/tools/commoncryptogenerator/CommonDigestGenerator.cs b/mcs/tools/commoncryptogenerator/CommonDigestGenerator.cs
new file mode 100644 (file)
index 0000000..1b729e3
--- /dev/null
@@ -0,0 +1,167 @@
+//
+// CommonCrypto code generator for digest algorithms
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012-2014 Xamarin Inc.
+//
+
+using System;
+using System.IO;
+
+namespace Xamarin {
+
+       public static class CommonDigest {
+               
+#if !MONOTOUCH && !XAMMAC
+               // we do not add anything in MonoTouch, just replacing, so this is not needed
+               // however we can avoid a dependency on Mono.Security for Crimson.CommonCrypto.dll by including the base classes
+               static public void GenerateBaseClass (string namespaceName, string typeName, string baseTypeName, int hashSize,
+                       string visibilityStart = "", string visibilityEnd = "")
+               {
+                       string template = @"// Generated file to bind CommonCrypto/CommonDigest - DO NOT EDIT
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012-2014 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+using System.Runtime.InteropServices;
+
+namespace %NAMESPACE% {
+
+%VISIBILITY_START%
+       public
+%VISIBILITY_END%
+       abstract class %BASE% : HashAlgorithm {
+
+               protected %BASE% () 
+               {
+                       HashSizeValue = %HASHSIZE%; 
+               }
+
+               public static new %BASE% Create ()
+               {
+                       return Create (""%BASE%"");
+               }
+
+               public static new %BASE% Create (string hashName)
+               {
+                       object o = CryptoConfig.CreateFromName (hashName);
+                       return (%BASE%) o ?? new %TYPE% ();
+               }
+       }
+}";
+                       
+                       File.WriteAllText (baseTypeName + ".g.cs", template.Replace ("%NAMESPACE%", namespaceName).
+                               Replace ("%TYPE%", typeName).Replace ("%BASE%", baseTypeName).
+                               Replace ("%VISIBILITY_START%", visibilityStart).Replace ("%VISIBILITY_END%", visibilityEnd).
+                               Replace ("%HASHSIZE%", hashSize.ToString ()));
+               }
+#endif
+               static public void Generate (string namespaceName, string typeName, string baseTypeName, int contextSize,
+                       string visibilityStart = "", string visibilityEnd = "")
+               {
+                       string template = @"// Generated file to bind CommonCrypto/CommonDigest - DO NOT EDIT
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2011-2014 Xamarin Inc.
+
+using System;
+using System.Security.Cryptography;
+using System.Runtime.InteropServices;
+
+using Mono.Security.Cryptography;
+
+namespace %NAMESPACE% {
+
+%VISIBILITY_START%
+       public
+%VISIBILITY_END%
+       sealed class %TYPE% : %BASE% {
+
+               IntPtr ctx;
+
+               [DllImport (""/usr/lib/libSystem.dylib"", EntryPoint=""CC_%BASE%_Init"")]
+               static extern int Init (/* CC_%BASE%_CTX */ IntPtr c);
+
+               [DllImport (""/usr/lib/libSystem.dylib"", EntryPoint=""CC_%BASE%_Update"")]
+               static extern int Update (/* CC_%BASE%_CTX */ IntPtr c, /* const void * */ IntPtr data, /* uint32_t */ uint len);
+
+               [DllImport (""/usr/lib/libSystem.dylib"", EntryPoint=""CC_%BASE%_Final"")]
+               static extern int Final (/* unsigned char * */ byte [] md, /* CC_%BASE%_CTX */ IntPtr c);
+
+               public %TYPE% ()
+               {
+                       ctx = IntPtr.Zero;
+               }
+
+               ~%TYPE% ()
+               {
+                       Dispose (false);
+               }
+
+               protected override void Dispose (bool disposing)
+               {
+                       if (ctx != IntPtr.Zero) {
+                               Marshal.FreeHGlobal (ctx);
+                               ctx = IntPtr.Zero;
+                       }
+                       base.Dispose (disposing);
+                       GC.SuppressFinalize (this);
+               }
+
+               public override void Initialize ()
+               {
+                       if (ctx == IntPtr.Zero)
+                               ctx = Marshal.AllocHGlobal (%CTX_SIZE%);
+                       
+                       int hr = Init (ctx);
+                       if (hr != 1)
+                               throw new CryptographicException (hr);
+               }
+
+               protected override void HashCore (byte[] data, int start, int length) 
+               {
+                       if (ctx == IntPtr.Zero)
+                               Initialize ();
+
+                       if (data.Length == 0)
+                               return;
+
+                       unsafe {
+                               fixed (byte* p = &data [0]) {
+                                       int hr = Update (ctx, (IntPtr) (p + start), (uint) length);
+                                       if (hr != 1)
+                                               throw new CryptographicException (hr);
+                               }
+                       }
+               }
+
+               protected override byte[] HashFinal () 
+               {
+                       if (ctx == IntPtr.Zero)
+                               Initialize ();
+                       
+                       byte[] data = new byte [HashSize >> 3];
+                       int hr = Final (data, ctx);
+                       if (hr != 1)
+                               throw new CryptographicException (hr);
+
+                       return data;
+               }
+       }
+}";
+                       
+                       File.WriteAllText (typeName + ".g.cs", template.Replace ("%NAMESPACE%", namespaceName).
+                               Replace ("%TYPE%", typeName).Replace ("%BASE%", baseTypeName).
+                               Replace ("%VISIBILITY_START%", visibilityStart).Replace ("%VISIBILITY_END%", visibilityEnd).
+                               Replace ("%CTX_SIZE%", contextSize.ToString ()));
+               }
+       }
+}
diff --git a/mcs/tools/commoncryptogenerator/Makefile b/mcs/tools/commoncryptogenerator/Makefile
new file mode 100644 (file)
index 0000000..64c52e4
--- /dev/null
@@ -0,0 +1,11 @@
+thisdir = tools/commoncryptogenerator
+SUBDIRS =
+include ../../build/rules.make
+
+LIB_REFS = 
+LOCAL_MCS_FLAGS =
+
+PROGRAM = commoncryptogenerator.exe
+NO_INSTALL = yes
+
+include ../../build/executable.make
diff --git a/mcs/tools/commoncryptogenerator/commoncryptogenerator.exe.sources b/mcs/tools/commoncryptogenerator/commoncryptogenerator.exe.sources
new file mode 100644 (file)
index 0000000..e2ecba4
--- /dev/null
@@ -0,0 +1,3 @@
+CommonCryptorGenerator.cs
+generator.cs
+CommonDigestGenerator.cs
diff --git a/mcs/tools/commoncryptogenerator/generator.cs b/mcs/tools/commoncryptogenerator/generator.cs
new file mode 100644 (file)
index 0000000..a7d13c8
--- /dev/null
@@ -0,0 +1,57 @@
+//
+// CommonCrypto Code Generator
+//
+// Authors:
+//     Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2012 Xamarin Inc.
+//
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Text;
+
+namespace Xamarin {
+       
+       class Program {
+               static void Main (string [] args)
+               {
+                       // mscorlib replacements
+                       CommonDigest.Generate ("System.Security.Cryptography", "MD5CryptoServiceProvider", "MD5", 1000);
+                       CommonDigest.Generate ("System.Security.Cryptography", "SHA1CryptoServiceProvider", "SHA1", 1000);
+                       CommonDigest.Generate ("System.Security.Cryptography", "SHA1Managed", "SHA1", 1000);
+                       CommonDigest.Generate ("System.Security.Cryptography", "SHA256Managed", "SHA256", 1000);
+                       CommonDigest.Generate ("System.Security.Cryptography", "SHA384Managed", "SHA384", 1000);
+                       CommonDigest.Generate ("System.Security.Cryptography", "SHA512Managed", "SHA512", 1000);
+                       
+                       // System.Core replacements - not yet in MT profile (4.0 - functional dupes anyway)
+                       //CommonDigest.Generate ("System.Security.Cryptography", "MD5Cng", "MD5", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA256Cng", "SHA256", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA384Cng", "SHA384", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA512Cng", "SHA512", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA256CryptoServiceProvider", "SHA256", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA384CryptoServiceProvider", "SHA384", 1000);
+                       //CommonDigest.Generate ("System.Security.Cryptography", "SHA512CryptoServiceProvider", "SHA512", 1000);
+                       
+                       // Mono.Security replacements
+                       CommonDigest.Generate ("Mono.Security.Cryptography", "MD2Managed", "MD2", 1000, "#if !INSIDE_CORLIB", "#endif");
+                       CommonDigest.Generate ("Mono.Security.Cryptography", "MD4Managed", "MD4", 1000, "#if !INSIDE_CORLIB", "#endif");
+                       CommonDigest.Generate ("Mono.Security.Cryptography", "SHA224Managed", "SHA224", 1000);
+
+                       // mscorlib replacements
+                       CommonCryptor.Generate ("System.Security.Cryptography", "DESCryptoServiceProvider", "DES", "DES");
+                       CommonCryptor.Generate ("System.Security.Cryptography", "TripleDESCryptoServiceProvider", "TripleDES", "TripleDES");
+                       CommonCryptor.Generate ("System.Security.Cryptography", "RC2CryptoServiceProvider", "RC2", "RC2", ctorInitializers: "LegalKeySizesValue = new[] { new KeySizes(40, 128, 8) };");
+                       // Rijndael supports block sizes that are not available in AES - as such it does not use the same generated code
+                       // but has it's own version, using AES (128 bits block size) and falling back to managed (192/256 bits block size)
+
+                       // System.Core replacements
+                       CommonCryptor.Generate ("System.Security.Cryptography", "AesManaged", "Aes", "AES128", "128");
+                       CommonCryptor.Generate ("System.Security.Cryptography", "AesCryptoServiceProvider", "Aes", "AES128");
+
+                       // Mono.Security replacements
+                       // RC4 is a stream (not a block) cipher so it can not reuse the generated code
+               }
+       }
+}
\ No newline at end of file
index 2e0ec2bc8dfc4da1721c9a7697a0eebc2be24c50..b3c2a5a450a7ee009eca10d6f239be79fa13af8b 100644 (file)
@@ -5,6 +5,7 @@ include ../../build/rules.make
 PROGRAM = compiler-tester.exe
 NO_INSTALL = yes
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Core.dll -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System System.Core System.Xml
 
 include $(topdir)/build/executable.make
index beafdfa555778472afda9b56e0d11d2fd3d52845..ec7e9dfc25a13881ee7e8ae8e0dec25750fc879e 100644 (file)
@@ -1440,17 +1440,15 @@ namespace TestRunner {
                static bool TryToMatchErrorMessage (string actual, string expected)
                {
                        actual = actual.Replace ("\\", "/");
-                       var path_mask_start = expected.IndexOf ("*PATH*");
+                       var path_mask_start = expected.IndexOf ("*PATH*", StringComparison.Ordinal);
                        if (path_mask_start > 0 && actual.Length > path_mask_start) {
-                               var path_mask_continue = expected.Substring (path_mask_start + 6);
-                               var expected_continue = actual.IndexOf (path_mask_continue, path_mask_start);
-                               if (expected_continue > 0) {
-                                       var path = actual.Substring (path_mask_start, expected_continue - path_mask_start);
-                                       if (actual == expected.Replace ("*PATH*", path))
-                                               return true;
-
-                                       throw new ApplicationException (expected.Replace ("*PATH*", path));
+                               var parts = expected.Split (new [] { "*PATH*" }, StringSplitOptions.None);
+                               foreach (var part in parts) {
+                                       if (!actual.Contains (part))
+                                               return false;
                                }
+
+                               return true;
                        }
 
                        return false;
index 17d843975055ef2db7672acb490f7a395f57f953..2f4a664387a5e0a0cba898163b21250e876f4b04 100644 (file)
@@ -2,45 +2,9 @@ thisdir = tools/corcompare
 SUBDIRS =
 include ../../build/rules.make
 
-ALL_PROGRAMS = mono-api-info.exe
+LIB_REFS = Mono.Cecil System.Xml System.Core System
+LOCAL_MCS_FLAGS =
 
-COMMON_SOURCES = \
-       AssemblyResolver.cs     \
-       Util.cs \
-       WellFormedXmlWriter.cs
+PROGRAM = mono-api-info.exe
 
-PROGRAM_INSTALL_DIR = $(mono_libdir)/mono/$(FRAMEWORK_VERSION)
-
-APIINFO_SOURCES = \
-       mono-api-info.cs \
-       ../../class/Mono.Options/Mono.Options/Options.cs \
-       $(COMMON_SOURCES)
-
-DISTFILES= $(COMMON_SOURCES) $(APIINFO_SOURCES)
-
-all-local: $(ALL_PROGRAMS)
-
-csproj-local doc-update-local:
-
-install-local: $(ALL_PROGRAMS)
-       $(MKINSTALLDIRS) $(DESTDIR)$(PROGRAM_INSTALL_DIR)
-       for i in $(ALL_PROGRAMS) ; do \
-               $(INSTALL_BIN) $$i $(DESTDIR)$(PROGRAM_INSTALL_DIR) ; \
-       done
-
-uninstall-local:
-       for i in $(ALL_PROGRAMS) ; do \
-           rm -f $(DESTDIR)$(PROGRAM_INSTALL_DIR)/`basename $$i` ; \
-       done
-
-test-local:
-
-run-test-local run-test-ondotnet-local:
-
-clean-local:
-       rm -f *.exe *.pdb
-
-dist-local: dist-default
-
-mono-api-info.exe: $(APIINFO_SOURCES) ../../class/Mono.Options/Mono.Options/Options.cs
-       $(CSCOMPILE) -r:Mono.Cecil.dll -r:System.Xml.dll -r:System.Core.dll -r:System.dll -out:$@ $^
+include ../../build/executable.make
diff --git a/mcs/tools/corcompare/mono-api-html/ApiChange.cs b/mcs/tools/corcompare/mono-api-html/ApiChange.cs
deleted file mode 100644 (file)
index 1d902ca..0000000
+++ /dev/null
@@ -1,81 +0,0 @@
-using System;
-using System.Collections.Generic;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff
-{
-       public class ApiChange
-       {
-               public string Header;
-               public StringBuilder Member = new StringBuilder ();
-               public bool Breaking;
-               public bool AnyChange;
-               public bool HasIgnoredChanges;
-
-               public ApiChange Append (string text)
-               {
-                       Member.Append (text);
-                       return this;
-               }
-
-               public ApiChange AppendAdded (string text, bool breaking = false)
-               {
-                       Member.Append ("<span class='added ").Append (breaking ? "added-breaking-inline" : string.Empty).Append ("'>");
-                       Member.Append (text);
-                       Member.Append ("</span>");
-                       Breaking |= breaking;
-                       AnyChange = true;
-                       return this;
-               }
-
-               public ApiChange AppendRemoved (string text, bool breaking = true)
-               {
-                       Member.Append ("<span class='removed removed-inline ").Append (breaking ? "removed-breaking-inline" : string.Empty).Append ("'>");
-                       Member.Append (text);
-                       Member.Append ("</span>");
-                       Breaking |= breaking;
-                       AnyChange = true;
-                       return this;
-               }
-
-               public ApiChange AppendModified (string old, string @new, bool breaking = true)
-               {
-                       if (old.Length > 0)
-                               AppendRemoved (old, breaking);
-                       if (old.Length > 0 && @new.Length > 0)
-                               Append (" ");
-                       if (@new.Length > 0)
-                               AppendAdded (@new);
-                       Breaking |= breaking;
-                       AnyChange = true;
-                       return this;
-               }
-       }
-
-       public class ApiChanges : Dictionary<string, List<ApiChange>> {
-               public void Add (XElement source, XElement target, ApiChange change)
-               {
-                       if (!change.AnyChange) {
-                               // This is most likely because the rendering doesn't take into account something that's different (solution: fix rendering).
-                               if (!change.HasIgnoredChanges) {
-                                       var isField = source.Name.LocalName == "field";
-                                       if (isField) {
-                                               Console.WriteLine ("Comparison resulting in no changes (src: {2} dst: {3}) :\n{0}\n{1}\n\n", source.ToString (), target.ToString (), source.GetFieldAttributes (), target.GetFieldAttributes ());
-                                       } else {
-                                               Console.WriteLine ("Comparison resulting in no changes (src: {2} dst: {3}) :\n{0}\n{1}\n\n", source.ToString (), target.ToString (), source.GetMethodAttributes (), target.GetMethodAttributes ());
-                                       }
-                               }
-                               return;
-                       }
-
-                       List<ApiChange> list;
-                       if (!TryGetValue (change.Header, out list)) {
-                               list = new List<ApiChange> ();
-                               base.Add (change.Header, list);
-                       }
-                       list.Add (change);
-               }
-       }
-}
-
diff --git a/mcs/tools/corcompare/mono-api-html/ApiDiff.cs b/mcs/tools/corcompare/mono-api-html/ApiDiff.cs
deleted file mode 100644 (file)
index 8fe2784..0000000
+++ /dev/null
@@ -1,277 +0,0 @@
-//
-// The main differences with mono-api-diff are:
-// * this tool directly produce HTML similar to gdiff.sh used for Xamarin.iOS
-// * this tool reports changes in an "evolutionary" way, not in a breaking way,
-//   i.e. it does not assume the source assembly is right (but simply older)
-// * the diff .xml output was not easy to convert back into the HTML format
-//   that gdiff.sh produced
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.IO;
-using System.Collections.Generic;
-using System.Text.RegularExpressions;
-
-using Mono.Options;
-
-namespace Xamarin.ApiDiff {
-
-       public static class State {
-               static TextWriter output;
-
-               public static TextWriter Output { 
-                       get {
-                               if (output == null)
-                                       output = Console.Out;
-                               return output;
-                       }
-                       set { output = value; } 
-               }
-
-               public static string Assembly { get; set; }
-               public static string Namespace { get; set; }
-               public static string Type { get; set; }
-               public static string BaseType { get; set; }
-
-               public static int Indent { get; set; }
-
-               static List<Regex> ignoreAdded = new List<Regex> ();
-               public static List<Regex> IgnoreAdded {
-                       get { return ignoreAdded; }
-               }
-
-               static List<Regex> ignoreNew = new List<Regex> ();
-               public static List<Regex> IgnoreNew {
-                       get { return ignoreNew; }
-               }
-
-               static List<Regex> ignoreRemoved = new List<Regex> ();
-               public static List<Regex> IgnoreRemoved {
-                       get { return ignoreRemoved; }
-               }
-
-               public  static  bool    IgnoreParameterNameChanges  { get; set; }
-               public  static  bool    IgnoreVirtualChanges        { get; set; }
-               public  static  bool    IgnoreAddedPropertySetters  { get; set; }
-
-               public static bool Lax;
-               public static bool Colorize = true;
-       }
-
-       class Program {
-
-               public static int Main (string[] args)
-               {
-                       var showHelp = false;
-                       string diff = null;
-                       List<string> extra = null;
-
-                       var options = new OptionSet {
-                               { "h|help", "Show this help", v => showHelp = true },
-                               { "d|diff=", "HTML diff file out output (omit for stdout)", v => diff = v },
-                               { "i|ignore=", "Ignore new, added, and removed members whose description matches a given C# regular expression (see below).",
-                                       v => {
-                                               var r = new Regex (v);
-                                               State.IgnoreAdded.Add (r);
-                                               State.IgnoreRemoved.Add (r);
-                                               State.IgnoreNew.Add (r);
-                                       }
-                               },
-                               { "a|ignore-added=", "Ignore added members whose description matches a given C# regular expression (see below).",
-                                       v => State.IgnoreAdded.Add (new Regex (v))
-                               },
-                               { "r|ignore-removed=", "Ignore removed members whose description matches a given C# regular expression (see below).",
-                                       v => State.IgnoreRemoved.Add (new Regex (v))
-                               },
-                               { "n|ignore-new=", "Ignore new namespaces and types whose description matches a given C# regular expression (see below).",
-                                       v => State.IgnoreNew.Add (new Regex (v))
-                               },
-                               { "ignore-changes-parameter-names", "Ignore changes to parameter names for identically prototyped methods.",
-                                       v => State.IgnoreParameterNameChanges   = v != null
-                               },
-                               { "ignore-changes-property-setters", "Ignore adding setters to properties.",
-                                       v => State.IgnoreAddedPropertySetters = v != null
-                               },
-                               { "ignore-changes-virtual", "Ignore changing non-`virtual` to `virtual` or adding `override`.",
-                                       v => State.IgnoreVirtualChanges = v != null
-                               },
-                               { "c|colorize:", "Colorize HTML output", v => State.Colorize = string.IsNullOrEmpty (v) ? true : bool.Parse (v) },
-                               { "x|lax", "Ignore duplicate XML entries", v => State.Lax = true }
-                       };
-
-                       try {
-                               extra = options.Parse (args);
-                       } catch (OptionException e) {
-                               Console.WriteLine ("Option error: {0}", e.Message);
-                               showHelp = true;
-                       }
-
-                       if (showHelp || extra == null || extra.Count < 2 || extra.Count > 3) {
-                               Console.WriteLine (@"Usage: mono-api-html [options] <reference.xml> <assembly.xml> [diff.html]");
-                               Console.WriteLine ();
-                               Console.WriteLine ("Available options:");
-                               options.WriteOptionDescriptions (Console.Out);
-                               Console.WriteLine ();
-                               Console.WriteLine ("Ignoring Members:");
-                               Console.WriteLine ();
-                               Console.WriteLine ("  Members that were added can be filtered out of the diff by using the");
-                               Console.WriteLine ("  -i, --ignore-added option. The option takes a C# regular expression");
-                               Console.WriteLine ("  to match against member descriptions. For example, to ignore the");
-                               Console.WriteLine ("  introduction of the interfaces 'INSCopying' and 'INSCoding' on types");
-                               Console.WriteLine ("  pass the following to mono-api-html:");
-                               Console.WriteLine ();
-                               Console.WriteLine ("    mono-api-html ... -i 'INSCopying$' -i 'INSCoding$'");
-                               Console.WriteLine ();
-                               Console.WriteLine ("  The regular expressions will match any member description ending with");
-                               Console.WriteLine ("  'INSCopying' or 'INSCoding'.");
-                               Console.WriteLine ();
-                               return 1;
-                       }
-
-                       var input = extra [0];
-                       var output = extra [1];
-                       if (extra.Count == 3 && diff == null)
-                               diff = extra [2];
-
-                       try {
-                               var ac = new AssemblyComparer (input, output);
-                               if (diff != null) {
-                                       string diffHtml = String.Empty;
-                                       using (var writer = new StringWriter ()) {
-                                               State.Output = writer;
-                                               ac.Compare ();
-                                               diffHtml = State.Output.ToString ();
-                                       }
-                                       if (diffHtml.Length > 0) {
-                                               using (var file = new StreamWriter (diff)) {
-                                                       file.WriteLine ("<div>");
-                                                       if (State.Colorize) {
-                                                               file.WriteLine ("<style scoped>");
-                                                               file.WriteLine ("\t.obsolete { color: gray; }");
-                                                               file.WriteLine ("\t.added { color: green; }");
-                                                               file.WriteLine ("\t.removed-inline { text-decoration: line-through; }");
-                                                               file.WriteLine ("\t.removed-breaking-inline { color: red;}");
-                                                               file.WriteLine ("\t.added-breaking-inline { text-decoration: underline; }");
-                                                               file.WriteLine ("\t.nonbreaking { color: black; }");
-                                                               file.WriteLine ("\t.breaking { color: red; }");
-                                                               file.WriteLine ("</style>");
-                                                       }
-                                                       file.WriteLine (
-@"<script type=""text/javascript"">
-       // Only some elements have 'data-is-[non-]breaking' attributes. Here we
-       // iterate over all descendents elements, and set 'data-is-[non-]breaking'
-       // depending on whether there are any descendents with that attribute.
-       function propagateDataAttribute (element)
-       {
-               if (element.hasAttribute ('data-is-propagated'))
-                       return;
-
-               var i;
-               var any_breaking = element.hasAttribute ('data-is-breaking');
-               var any_non_breaking = element.hasAttribute ('data-is-non-breaking');
-               for (i = 0; i < element.children.length; i++) {
-                       var el = element.children [i];
-                       propagateDataAttribute (el);
-                       any_breaking |= el.hasAttribute ('data-is-breaking');
-                       any_non_breaking |= el.hasAttribute ('data-is-non-breaking');
-               }
-               
-               if (any_breaking)
-                       element.setAttribute ('data-is-breaking', null);
-               else if (any_non_breaking)
-                       element.setAttribute ('data-is-non-breaking', null);
-               element.setAttribute ('data-is-propagated', null);
-       }
-
-       function hideNonBreakingChanges ()
-       {
-               var topNodes = document.querySelectorAll ('[data-is-topmost]');
-               var n;
-               var i;
-               for (n = 0; n < topNodes.length; n++) {
-                       propagateDataAttribute (topNodes [n]);
-                       var elements = topNodes [n].querySelectorAll ('[data-is-non-breaking]');
-                       for (i = 0; i < elements.length; i++) {
-                               var el = elements [i];
-                               if (!el.hasAttribute ('data-original-display'))
-                                       el.setAttribute ('data-original-display', el.style.display);
-                               el.style.display = 'none';
-                       }
-               }
-               
-               var links = document.getElementsByClassName ('hide-nonbreaking');
-               for (i = 0; i < links.length; i++)
-                       links [i].style.display = 'none';
-               links = document.getElementsByClassName ('restore-nonbreaking');
-               for (i = 0; i < links.length; i++)
-                       links [i].style.display = '';
-       }
-
-       function showNonBreakingChanges ()
-       {
-               var elements = document.querySelectorAll ('[data-original-display]');
-               var i;
-               for (i = 0; i < elements.length; i++) {
-                       var el = elements [i];
-                       el.style.display = el.getAttribute ('data-original-display');
-               }
-
-               var links = document.getElementsByClassName ('hide-nonbreaking');
-               for (i = 0; i < links.length; i++)
-                       links [i].style.display = '';
-               links = document.getElementsByClassName ('restore-nonbreaking');
-               for (i = 0; i < links.length; i++)
-                       links [i].style.display = 'none';
-       }
-</script>");
-                                                       if (ac.SourceAssembly == ac.TargetAssembly) {
-                                                               file.WriteLine ("<h1>{0}.dll</h1>", ac.SourceAssembly);
-                                                       } else {
-                                                               file.WriteLine ("<h1>{0}.dll vs {1}.dll</h1>", ac.SourceAssembly, ac.TargetAssembly);
-                                                       }
-                                                       file.WriteLine ("<a href='javascript: hideNonBreakingChanges (); ' class='hide-nonbreaking'>Hide non-breaking changes</a>");
-                                                       file.WriteLine ("<a href='javascript: showNonBreakingChanges (); ' class='restore-nonbreaking' style='display: none;'>Show non-breaking changes</a>");
-                                                       file.WriteLine ("<br/>");
-                                                       file.WriteLine ("<div data-is-topmost>");
-                                                       file.Write (diffHtml);
-                                                       file.WriteLine ("</div> <!-- end topmost div -->");
-                                                       file.WriteLine ("</div>");
-                                               }
-                                       }
-                               } else {
-                                       State.Output = Console.Out;
-                                       ac.Compare ();
-                               }
-                       }
-                       catch (Exception e) {
-                               Console.WriteLine (e);
-                               return 1;
-                       }
-                       return 0;
-               }
-       }
-}
diff --git a/mcs/tools/corcompare/mono-api-html/AssemblyComparer.cs b/mcs/tools/corcompare/mono-api-html/AssemblyComparer.cs
deleted file mode 100644 (file)
index adbd862..0000000
+++ /dev/null
@@ -1,79 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class AssemblyComparer : Comparer {
-
-               XDocument source;
-               XDocument target;
-               NamespaceComparer comparer;
-
-               public AssemblyComparer (string sourceFile, string targetFile)
-               {
-                       source = XDocument.Load (sourceFile);
-                       target = XDocument.Load (targetFile);
-                       comparer =  new NamespaceComparer ();
-               }
-
-               public string SourceAssembly { get; private set; }
-               public string TargetAssembly { get; private set; }
-
-               public void Compare ()
-               {
-                       Compare (source.Element ("assemblies").Elements ("assembly"), 
-                                target.Element ("assemblies").Elements ("assembly"));
-               }
-
-               public override void SetContext (XElement current)
-               {
-                       State.Assembly = current.GetAttribute ("name");
-               }
-
-               public override void Added (XElement target, bool wasParentAdded)
-               {
-                       // one assembly per xml file
-               }
-
-               public override void Modified (XElement source, XElement target, ApiChanges diff)
-               {
-                       SourceAssembly = source.GetAttribute ("name");
-                       TargetAssembly = target.GetAttribute ("name");
-                       // TODO: version
-                       // ? custom attributes ?
-                       comparer.Compare (source, target);
-               }
-
-               public override void Removed (XElement source)
-               {
-                       // one assembly per xml file
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/ClassComparer.cs b/mcs/tools/corcompare/mono-api-html/ClassComparer.cs
deleted file mode 100644 (file)
index a3399fb..0000000
+++ /dev/null
@@ -1,261 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.IO;
-using System.Linq;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class ClassComparer : Comparer {
-
-               InterfaceComparer icomparer;
-               ConstructorComparer ccomparer;
-               FieldComparer fcomparer;
-               PropertyComparer pcomparer;
-               EventComparer ecomparer;
-               MethodComparer mcomparer;
-               ClassComparer kcomparer;
-
-               public ClassComparer ()
-               {
-                       icomparer = new InterfaceComparer ();
-                       ccomparer = new ConstructorComparer ();
-                       fcomparer = new FieldComparer ();
-                       pcomparer = new PropertyComparer ();
-                       ecomparer = new EventComparer ();
-                       mcomparer = new MethodComparer ();
-               }
-
-               public override void SetContext (XElement current)
-               {
-                       State.Type = current.GetAttribute ("name");
-                       State.BaseType = current.GetAttribute ("base");
-               }
-
-               public void Compare (XElement source, XElement target)
-               {
-                       var s = source.Element ("classes");
-                       var t = target.Element ("classes");
-                       if (XNode.DeepEquals (s, t))
-                               return;
-                       Compare (s.Elements ("class"), t.Elements ("class"));
-               }
-
-               public override void Added (XElement target, bool wasParentAdded)
-               {
-                       string name = target.Attribute ("name").Value;
-                       if (State.IgnoreNew.Any (re => re.IsMatch (name)))
-                               return;
-                       Output.WriteLine ("<div> <!-- start type {0} -->", name);
-                       Output.WriteLine ("<h3>New Type {0}.{1}</h3>", State.Namespace, name);
-                       Output.WriteLine ("<pre class='added' data-is-non-breaking>");
-                       State.Indent = 0;
-                       AddedInner (target);
-                       Output.WriteLine ("</pre>");
-                       Output.WriteLine ("</div> <!-- end type {0} -->", name);
-               }
-
-               public void AddedInner (XElement target)
-               {
-                       SetContext (target);
-                       if (target.IsTrue ("serializable"))
-                               Indent ().WriteLine ("[Serializable]");
-
-                       var type = target.Attribute ("type").Value;
-
-                       if (type == "enum") {
-                               // check if [Flags] is present
-                               var cattrs = target.Element ("attributes");
-                               if (cattrs != null) {
-                                       foreach (var ca in cattrs.Elements ("attribute")) {
-                                               if (ca.GetAttribute ("name") == "System.FlagsAttribute") {
-                                                       Indent ().WriteLine ("[Flags]");
-                                                       break;
-                                               }
-                                       }
-                               }
-                       }
-
-                       Indent ().Write ("public");
-
-                       if (type != "enum") {
-                               bool seal = target.IsTrue ("sealed");
-                               bool abst = target.IsTrue ("abstract");
-                               if (seal && abst)
-                                       Output.Write (" static");
-                               else if (seal && type != "struct")
-                                       Output.Write (" sealed");
-                               else if (abst && type != "interface")
-                                       Output.Write (" abstract");
-                       }
-
-                       Output.Write (' ');
-                       Output.Write (type);
-                       Output.Write (' ');
-                       Output.Write (target.GetAttribute ("name"));
-
-                       var baseclass = target.GetAttribute ("base");
-                       if ((type != "enum") && (type != "struct")) {
-                               if (baseclass != null) {
-                                       if (baseclass == "System.Object") {
-                                               // while true we do not need to be reminded every time...
-                                               baseclass = null;
-                                       } else {
-                                               Output.Write (" : ");
-                                               Output.Write (baseclass);
-                                       }
-                               }
-                       }
-
-                       // interfaces on enums are "standard" not user provided - so we do not want to show them
-                       if (type != "enum") {
-                               var i = target.Element ("interfaces");
-                               if (i != null) {
-                                       var interfaces = new List<string> ();
-                                       foreach (var iface in i.Elements ("interface"))
-                                               interfaces.Add (icomparer.GetDescription (iface));
-                                       Output.Write ((baseclass == null) ? " : " : ", ");
-                                       Output.Write (String.Join (", ", interfaces));
-                               }
-                       }
-
-                       Output.WriteLine (" {");
-
-                       var t = target.Element ("constructors");
-                       if (t != null) {
-                               Indent ().WriteLine ("\t// constructors");
-                               foreach (var ctor in t.Elements ("constructor"))
-                                       ccomparer.Added (ctor, true);
-                       }
-
-                       t = target.Element ("fields");
-                       if (t != null) {
-                               if (type != "enum")
-                                       Indent ().WriteLine ("\t// fields");
-                               else
-                                       SetContext (target);
-                               foreach (var field in t.Elements ("field"))
-                                       fcomparer.Added (field, true);
-                       }
-
-                       t = target.Element ("properties");
-                       if (t != null) {
-                               Indent ().WriteLine ("\t// properties");
-                               foreach (var property in t.Elements ("property"))
-                                       pcomparer.Added (property, true);
-                       }
-
-                       t = target.Element ("events");
-                       if (t != null) {
-                               Indent ().WriteLine ("\t// events");
-                               foreach (var evnt in t.Elements ("event"))
-                                       ecomparer.Added (evnt, true);
-                       }
-
-                       t = target.Element ("methods");
-                       if (t != null) {
-                               Indent ().WriteLine ("\t// methods");
-                               foreach (var method in t.Elements ("method"))
-                                       mcomparer.Added (method, true);
-                       }
-
-                       t = target.Element ("classes");
-                       if (t != null) {
-                               Output.WriteLine ();
-                               Indent ().WriteLine ("\t// inner types");
-                               kcomparer = new NestedClassComparer ();
-                               State.Indent++;
-                               foreach (var inner in t.Elements ("class"))
-                                       kcomparer.AddedInner (inner);
-                               State.Indent--;
-                       }
-                       Indent ().WriteLine ("}");
-               }
-
-               public override void Modified (XElement source, XElement target, ApiChanges diff)
-               {
-                       // hack - there could be changes that we're not monitoring (e.g. attributes properties)
-                       var output = Output;
-                       State.Output = new StringWriter ();
-
-                       var sb = source.GetAttribute ("base");
-                       var tb = target.GetAttribute ("base");
-                       if (sb != tb) {
-                               Output.Write ("Modified base type: ");
-                               Output.WriteLine (new ApiChange ().AppendModified (sb, tb, true).Member.ToString ());
-                       }
-
-                       ccomparer.Compare (source, target);
-                       icomparer.Compare (source, target);
-                       fcomparer.Compare (source, target);
-                       pcomparer.Compare (source, target);
-                       ecomparer.Compare (source, target);
-                       mcomparer.Compare (source, target);
-
-                       var si = source.Element ("classes");
-                       if (si != null) {
-                               var ti = target.Element ("classes");
-                               kcomparer = new NestedClassComparer ();
-                               kcomparer.Compare (si.Elements ("class"), ti == null ? null : ti.Elements ("class"));
-                       }
-
-                       var s = (Output as StringWriter).ToString ();
-                       State.Output = output;
-                       if (s.Length > 0) {
-                               var tn = GetTypeName (target);
-                               Output.WriteLine ("<!-- start type {0} --> <div>", tn);
-                               Output.WriteLine ("<h3>Type Changed: {0}.{1}</h3>", State.Namespace, GetTypeName (target));
-                               Output.WriteLine (s);
-                               Output.WriteLine ("</div> <!-- end type {0} -->", tn);
-                       }
-               }
-
-               public override void Removed (XElement source)
-               {
-                       Output.Write ("<h3>Removed Type <span class='breaking' data-is-breaking>{0}.{1}</span></h3>", State.Namespace, GetTypeName (source));
-               }
-
-               public virtual string GetTypeName (XElement type)
-               {
-                       return type.GetAttribute ("name");
-               }
-       }
-
-       public class NestedClassComparer : ClassComparer {
-
-               public override void SetContext (XElement current)
-               {
-               }
-
-               public override string GetTypeName (XElement type)
-               {
-                       return State.Type + "." + base.GetTypeName (type);
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/Comparer.cs b/mcs/tools/corcompare/mono-api-html/Comparer.cs
deleted file mode 100644 (file)
index 4210b9b..0000000
+++ /dev/null
@@ -1,98 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.IO;
-using System.Linq;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public abstract class Comparer {
-
-               protected List<XElement> removed = new List<XElement> ();
-               protected ApiChanges modified = new ApiChanges ();
-
-               public TextWriter Output {
-                       get { return State.Output; }
-               }
-
-               protected TextWriter Indent ()
-               {
-                       for (int i = 0; i < State.Indent; i++)
-                               State.Output.Write ("\t");
-                       return State.Output;
-               }
-
-               public abstract void Added (XElement target, bool wasParentAdded);
-               public abstract void Modified (XElement source, XElement target, ApiChanges changes);
-               public abstract void Removed (XElement source);
-
-               public virtual bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       return XNode.DeepEquals (source, target);
-               }
-
-               public abstract void SetContext (XElement current);
-
-               public virtual void Compare (IEnumerable<XElement> source, IEnumerable<XElement> target)
-               {
-                       removed.Clear ();
-                       modified.Clear ();
-
-                       foreach (var s in source) {
-                               SetContext (s);
-                               string sn = s.GetAttribute ("name");
-                               var t = target == null ? null : target.SingleOrDefault (x => x.GetAttribute ("name") == sn);
-                               if (t == null) {
-                                       // not in target, it was removed
-                                       removed.Add (s);
-                               } else {
-                                       t.Remove ();
-                                       // possibly modified
-                                       if (Equals (s, t, modified))
-                                               continue;
-
-                                       // still in target so will be part of Added
-                                       Modified (s, t, modified);
-                               }
-                       }
-                       // delayed, that way we show "Modified", "Added" and then "Removed"
-                       foreach (var item in removed) {
-                               SetContext (item);
-                               Removed (item);
-                       }
-                       // remaining == newly added in target
-                       if (target != null) {
-                               foreach (var item in target) {
-                                       SetContext (item);
-                                       Added (item, false);
-                               }
-                       }
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/ConstructorComparer.cs b/mcs/tools/corcompare/mono-api-html/ConstructorComparer.cs
deleted file mode 100644 (file)
index 9bd837e..0000000
+++ /dev/null
@@ -1,148 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Reflection;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       // MethodComparer inherits from this one
-       public class ConstructorComparer : MemberComparer {
-
-               public override string GroupName {
-                       get { return "constructors"; }
-               }
-
-               public override string ElementName {
-                       get { return "constructor"; }
-               }
-
-               public override bool Find (XElement e)
-               {
-                       return (e.Attribute ("name").Value == Source.Attribute ("name").Value);
-               }
-
-               void RenderReturnType (XElement source, XElement target, ApiChange change)
-               {
-                       var srcType = source.GetTypeName ("returntype");
-                       var tgtType = target.GetTypeName ("returntype");
-
-                       if (srcType != tgtType) {
-                               change.AppendModified (srcType, tgtType, true);
-                               change.Append (" ");
-                       } else if (srcType != null) {
-                               // ctor don't have a return type
-                               change.Append (srcType);
-                               change.Append (" ");
-                       }
-               }
-
-               public override bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       if (base.Equals (source, target, changes))
-                               return true;
-                               
-                       var change = new ApiChange ();
-                       change.Header = "Modified " + GroupName;
-                       RenderMethodAttributes (source, target, change);
-                       RenderReturnType (source, target, change);
-                       RenderName (source, target, change);
-                       RenderGenericParameters (source, target, change);
-                       RenderParameters (source, target, change);
-
-                       changes.Add (source, target, change);
-
-                       return false;
-               }
-
-               public override string GetDescription (XElement e)
-               {
-                       var sb = new StringBuilder ();
-
-                       var attribs = e.Attribute ("attrib");
-                       if (attribs != null) {
-                               var attr = (MethodAttributes) Int32.Parse (attribs.Value);
-                               if ((attr & MethodAttributes.Public) != MethodAttributes.Public) {
-                                       sb.Append ("protected ");
-                               } else {
-                                       sb.Append ("public ");
-                               }
-
-                               if ((attr & MethodAttributes.Static) != 0) {
-                                       sb.Append ("static ");
-                               } else if ((attr & MethodAttributes.Virtual) != 0) {
-                                       if ((attr & MethodAttributes.VtableLayoutMask) == 0)
-                                               sb.Append ("override ");
-                                       else
-                                               sb.Append ("virtual ");
-                               }
-                       }
-
-                       string name = e.GetAttribute ("name");
-
-                       var r = e.GetTypeName ("returntype");
-                       if (r != null) {
-                               // ctor dont' have a return type
-                               sb.Append (r).Append (' ');
-                       } else {
-                               // show the constructor as it would be defined in C#
-                               name = name.Replace (".ctor", State.Type);
-                       }
-
-                       // the XML file `name` does not contain parameter names, so we must process them ourselves
-                       // which gives us the opportunity to simplify type names
-                       sb.Append (name.Substring (0, name.IndexOf ('(')));
-
-                       var genericp = e.Element ("generic-parameters");
-                       if (genericp != null) {
-                               var list = new List<string> ();
-                               foreach (var p in genericp.Elements ("generic-parameter")) {
-                                       list.Add (p.GetTypeName ("name"));
-                               }
-                               sb.Append ("&lt;").Append (String.Join (", ", list)).Append ("&gt;");
-                       }
-
-                       sb.Append (" (");
-                       var parameters = e.Element ("parameters");
-                       if (parameters != null) {
-                               var list = new List<string> ();
-                               foreach (var p in parameters.Elements ("parameter")) {
-                                       var pTypeName   = p.GetTypeName ("type");
-                                       list.Add (State.IgnoreParameterNameChanges
-                                               ? pTypeName
-                                               : pTypeName + " " + p.GetAttribute ("name"));
-                               }
-                               sb.Append (String.Join (", ", list));
-                       }
-                       sb.Append (");");
-
-                       return sb.ToString ();
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/EventComparer.cs b/mcs/tools/corcompare/mono-api-html/EventComparer.cs
deleted file mode 100644 (file)
index 693f16f..0000000
+++ /dev/null
@@ -1,75 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class EventComparer : MemberComparer {
-
-               public override string GroupName {
-                       get { return "events"; }
-               }
-
-               public override string ElementName {
-                       get { return "event"; }
-               }
-
-               public override bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       if (base.Equals (source, target, changes))
-                               return true;
-
-                       var change = new ApiChange ();
-                       change.Header = "Modified " + GroupName;
-                       change.Append ("public event ");
-
-                       var srcEventType = source.GetTypeName ("eventtype");
-                       var tgtEventType = target.GetTypeName ("eventtype");
-
-                       if (srcEventType != tgtEventType) {
-                               change.AppendModified (srcEventType, tgtEventType, true);
-                       } else {
-                               change.Append (srcEventType);
-                       }
-                       change.Append (" ");
-                       change.Append (source.GetAttribute ("name")).Append (";");
-                       return false;
-               }
-
-               public override string GetDescription (XElement e)
-               {
-                       StringBuilder sb = new StringBuilder ();
-                       // TODO: attribs
-                       sb.Append ("public event ");
-                       sb.Append (e.GetTypeName ("eventtype")).Append (' ');
-                       sb.Append (e.GetAttribute ("name")).Append (';');
-                       return sb.ToString ();
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/FieldComparer.cs b/mcs/tools/corcompare/mono-api-html/FieldComparer.cs
deleted file mode 100644 (file)
index a2b0225..0000000
+++ /dev/null
@@ -1,211 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Reflection;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class FieldComparer : MemberComparer {
-
-               public override string GroupName {
-                       get { return "fields"; }
-               }
-
-               public override string ElementName {
-                       get { return "field"; }
-               }
-
-               void RenderFieldAttributes (FieldAttributes source, FieldAttributes target, ApiChange change)
-               {
-                       var srcNotSerialized = (source & FieldAttributes.NotSerialized) == FieldAttributes.NotSerialized;
-                       var tgtNotSerialized = (target & FieldAttributes.NotSerialized) == FieldAttributes.NotSerialized;
-                       if (srcNotSerialized != tgtNotSerialized) {
-                               // this is not a breaking change, so only render it if it changed.
-                               if (srcNotSerialized) {
-                                       change.AppendRemoved ("[NonSerialized]\n");
-                               } else {
-                                       change.AppendAdded ("[NonSerialized]\n");
-                               }
-                       }
-
-                       // the visibility values are the same for MethodAttributes and FieldAttributes, so just use the same method.
-                       RenderVisibility ((MethodAttributes) source, (MethodAttributes) target, change);
-                       // same for the static flag
-                       RenderStatic ((MethodAttributes) source, (MethodAttributes) target, change);
-
-                       var srcLiteral = (source & FieldAttributes.Literal) != 0;
-                       var tgtLiteral = (target & FieldAttributes.Literal) != 0;
-
-                       if (srcLiteral) {
-                               if (tgtLiteral) {
-                                       change.Append ("const ");
-                               } else {
-                                       change.AppendRemoved ("const", true).Append (" ");
-                               }
-                       } else if (tgtLiteral) {
-                               change.AppendAdded ("const", true).Append (" ");
-                       }
-
-                       var srcInitOnly = (source & FieldAttributes.InitOnly) != 0;
-                       var tgtInitOnly = (target & FieldAttributes.InitOnly) != 0;
-                       if (srcInitOnly) {
-                               if (tgtInitOnly) {
-                                       change.Append ("readonly ");
-                               } else {
-                                       change.AppendRemoved ("readonly", false).Append (" ");
-                               }
-                       } else if (tgtInitOnly) {
-                               change.AppendAdded ("readonly", true).Append (" ");
-                       }
-               }
-
-               public override bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       if (base.Equals (source, target, changes))
-                               return true;
-
-                       var name = source.GetAttribute ("name");
-                       var srcValue = source.GetAttribute ("value");
-                       var tgtValue = target.GetAttribute ("value");
-                       var change = new ApiChange ();
-                       change.Header = "Modified " + GroupName;
-
-                       if (State.BaseType == "System.Enum") {
-                               change.Append (name).Append (" = ");
-                               if (srcValue != tgtValue) {
-                                       change.AppendModified (srcValue, tgtValue, true);
-                               } else {
-                                       change.Append (srcValue);
-                               }
-                       } else {
-                               RenderFieldAttributes (source.GetFieldAttributes (), target.GetFieldAttributes (), change);
-
-                               var srcType = source.GetTypeName ("fieldtype");
-                               var tgtType = target.GetTypeName ("fieldtype");
-
-                               if (srcType != tgtType) {
-                                       change.AppendModified (srcType, tgtType, true);
-                               } else {
-                                       change.Append (srcType);
-                               }
-                               change.Append (" ");
-                               change.Append (name);
-
-                               if (srcType == "string" && srcValue != null)
-                                       srcValue = "\"" + srcValue + "\"";
-
-                               if (tgtType == "string" && tgtValue != null)
-                                       tgtValue = "\"" + tgtValue + "\"";
-
-                               if (srcValue != tgtValue) {
-                                       change.Append (" = ");
-                                       if (srcValue == null)
-                                               srcValue = "null";
-                                       if (tgtValue == null)
-                                               tgtValue = "null";
-                                       change.AppendModified (srcValue, tgtValue, true);
-                               } else if (srcValue != null) {
-                                       change.Append (" = ");
-                                       change.Append (srcValue);
-                               }
-                               change.Append (";");
-                       }
-
-                       changes.Add (source, target, change);
-
-                       return false;
-               }
-
-               public override string GetDescription (XElement e)
-               {
-                       var sb = new StringBuilder ();
-
-                       string name = e.GetAttribute ("name");
-                       string value = e.GetAttribute ("value");
-
-                       if (State.BaseType == "System.Enum") {
-                               sb.Append (name).Append (" = ").Append (value).Append (',');
-                       } else {
-                               var attribs = e.Attribute ("attrib");
-                               if (attribs != null) {
-                                       var attr = (FieldAttributes)Int32.Parse (attribs.Value);
-                                       if ((attr & FieldAttributes.Public) != FieldAttributes.Public) {
-                                               sb.Append ("protected ");
-                                       } else {
-                                               sb.Append ("public ");
-                                       }
-
-                                       if ((attr & FieldAttributes.Static) != 0)
-                                               sb.Append ("static ");
-
-                                       if ((attr & FieldAttributes.Literal) != 0)
-                                               sb.Append ("const ");
-                               }
-
-                               string ftype = e.GetTypeName ("fieldtype");
-                               sb.Append (ftype).Append (' ');
-                               sb.Append (name);
-                               if (ftype == "string" && e.Attribute ("value") != null) {
-                                       if (value == null)
-                                               sb.Append (" = null");
-                                       else
-                                               sb.Append (" = \"").Append (value).Append ('"');
-                               }
-                               sb.Append (';');
-                       }
-
-                       return sb.ToString ();
-               }
-
-               public override void BeforeAdding (IEnumerable<XElement> list)
-               {
-                       first = true;
-                       if (State.BaseType == "System.Enum") {
-                               Output.WriteLine ("<div>");
-                               Output.WriteLine ("<p>Added value{0}:</p>", list.Count () > 1 ? "s" : String.Empty);
-                               Output.WriteLine ("<pre class='added' data-is-non-breaking>");
-                       } else {
-                               base.BeforeAdding (list);
-                       }
-               }
-
-               public override void BeforeRemoving (IEnumerable<XElement> list)
-               {
-                       first = true;
-                       if (State.BaseType == "System.Enum") {
-                               Output.WriteLine ("<p>Removed value{0}:</p>", list.Count () > 1 ? "s" : String.Empty);
-                               Output.WriteLine ("<pre class='removed' data-is-breaking>");
-                       } else {
-                               base.BeforeRemoving (list);
-                       }
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/Helpers.cs b/mcs/tools/corcompare/mono-api-html/Helpers.cs
deleted file mode 100644 (file)
index 8769785..0000000
+++ /dev/null
@@ -1,207 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Reflection;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public static class Helper {
-               public static bool IsTrue (this XElement self, string name)
-               {
-                       return (self.GetAttribute (name) == "true");
-               }
-
-               public static string GetAttribute (this XElement self, string name)
-               {
-                       var n = self.Attribute (name);
-                       if (n == null)
-                               return null;
-                       return n.Value;
-               }
-
-               // null == no obsolete, String.Empty == no description
-               public static string GetObsoleteMessage (this XElement self)
-               {
-                       var cattrs = self.Element ("attributes");
-                       if (cattrs == null)
-                               return null;
-
-                       foreach (var ca in cattrs.Elements ("attribute")) {
-                               if (ca.GetAttribute ("name") != "System.ObsoleteAttribute")
-                                       continue;
-                               var props = ca.Element ("properties");
-                               if (props == null)
-                                       return String.Empty; // no description
-                               foreach (var p in props.Elements ("property")) {
-                                       if (p.GetAttribute ("name") != "Message")
-                                               continue;
-                                       return p.GetAttribute ("value");
-                               }
-                       }
-                       return null;
-               }
-
-               public static IEnumerable<XElement> Descendants (this XElement self, params string[] names)
-               {
-                       XElement el = self;
-                       if (el == null)
-                               return null;
-
-                       for (int i = 0; i < names.Length - 1; i++) {
-                               el = el.Element (names [i]);
-                               if (el == null)
-                                       return null;
-                       }
-                       return el.Elements (names [names.Length - 1]);
-               }
-
-               public static List<XElement> DescendantList (this XElement self, params string[] names)
-               {
-                       var descendants = self.Descendants (names);
-                       if (descendants == null)
-                               return null;
-                       return descendants.ToList ();
-               }
-
-               // make it beautiful (.NET -> C#)
-               public static string GetTypeName (this XElement self, string name)
-               {
-                       string type = self.GetAttribute (name);
-                       if (type == null)
-                               return null;
-
-                       StringBuilder sb = null;
-                       bool is_nullable = false;
-                       if (type.StartsWith ("System.Nullable`1[", StringComparison.Ordinal)) {
-                               is_nullable = true;
-                               sb = new StringBuilder (type, 18, type.Length - 19, 1024);
-                       } else {
-                               sb = new StringBuilder (type);
-                       }
-
-                       bool is_ref = (sb [sb.Length - 1] == '&');
-                       if (is_ref)
-                               sb.Remove (sb.Length - 1, 1);
-
-                       int array = 0;
-                       while ((sb [sb.Length - 1] == ']') && (sb [sb.Length - 2] == '[')) {
-                               sb.Remove (sb.Length - 2, 2);
-                               array++;
-                       }
-
-                       bool is_pointer = (sb [sb.Length - 1] == '*');
-                       if (is_pointer)
-                               sb.Remove (sb.Length - 1, 1);
-
-                       type = GetTypeName (sb.Replace ('+', '.').ToString ());
-                       sb.Length = 0;
-                       if (is_ref)
-                               sb.Append (self.GetAttribute ("direction")).Append (' ');
-
-                       sb.Append (type);
-
-                       while (array-- > 0)
-                               sb.Append ("[]");
-                       if (is_nullable)
-                               sb.Append ('?');
-                       if (is_pointer)
-                               sb.Append ('*');
-                       return sb.ToString ();
-               }
-
-               static string GetTypeName (string type)
-               {
-                       int pos = type.IndexOf ('`');
-                       if (pos >= 0) {
-                               int end = type.LastIndexOf (']');
-                               string subtype = type.Substring (pos + 3, end - pos - 3);
-                               return type.Substring (0, pos) + "&lt;" + GetTypeName (subtype) + "&gt;";
-                       }
-
-                       switch (type) {
-                       case "System.String":
-                               return "string";
-                       case "System.Int32":
-                               return "int";
-                       case "System.UInt32":
-                               return "uint";
-                       case "System.Int64":
-                               return "long";
-                       case "System.UInt64":
-                               return "ulong";
-                       case "System.Void":
-                               return "void";
-                       case "System.Boolean":
-                               return "bool";
-                       case "System.Object":
-                               return "object";
-                       case "System.Single":
-                               return "float";
-                       case "System.Double":
-                               return "double";
-                       case "System.Byte":
-                               return "byte";
-                       case "System.SByte":
-                               return "sbyte";
-                       case "System.Int16":
-                               return "short";
-                       case "System.UInt16":
-                               return "ushort";
-                       case "System.Char":
-                               return "char";
-                       case "System.nint":
-                               return "nint";
-                       case "System.nuint":
-                               return "uint";
-                       case "System.nfloat":
-                               return "nfloat";
-                       case "System.IntPtr":
-                               return "IntPtr";
-                       default:
-                               if (type.StartsWith (State.Namespace, StringComparison.Ordinal))
-                                       type = type.Substring (State.Namespace.Length + 1);
-                               return type;
-                       }
-               }
-
-               public static MethodAttributes GetMethodAttributes (this XElement element)
-               {
-                       var srcAttribs = element.Attribute ("attrib");
-                       return (MethodAttributes) (srcAttribs != null ? Int32.Parse (srcAttribs.Value) : 0);
-               }
-
-               public static FieldAttributes GetFieldAttributes (this XElement element)
-               {
-                       var srcAttribs = element.Attribute ("attrib");
-                       return (FieldAttributes) (srcAttribs != null ? Int32.Parse (srcAttribs.Value) : 0);
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/InterfaceComparer.cs b/mcs/tools/corcompare/mono-api-html/InterfaceComparer.cs
deleted file mode 100644 (file)
index df52f16..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class InterfaceComparer : MemberComparer {
-
-               public override string GroupName {
-                       get { return "interfaces"; }
-               }
-
-               public override string ElementName {
-                       get { return "interface"; }
-               }
-
-               public override string GetDescription (XElement e)
-               {
-                       return e.GetTypeName ("name");
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/MemberComparer.cs b/mcs/tools/corcompare/mono-api-html/MemberComparer.cs
deleted file mode 100644 (file)
index d12d866..0000000
+++ /dev/null
@@ -1,608 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Linq;
-using System.Reflection;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public abstract class MemberComparer : Comparer {
-
-               // true if this is the first element being added or removed in the group being rendered
-               protected bool first;
-
-               public abstract string GroupName { get; }
-               public abstract string ElementName { get; }
-
-               protected virtual bool IsBreakingRemoval (XElement e)
-               {
-                       return true;
-               }
-
-               public void Compare (XElement source, XElement target)
-               {
-                       var s = source.Element (GroupName);
-                       var t = target.Element (GroupName);
-                       if (XNode.DeepEquals (s, t))
-                               return;
-
-                       if (s == null) {
-                               Add (t.Elements (ElementName));
-                       } else if (t == null) {
-                               Remove (s.Elements (ElementName));
-                       } else {
-                               Compare (s.Elements (ElementName), t.Elements (ElementName));
-                       }
-               }
-
-               public override void SetContext (XElement current)
-               {
-               }
-
-               string GetContainingType (XElement el)
-               {
-                       return el.Ancestors ("class").First ().Attribute ("type").Value;
-               }
-
-               bool IsInInterface (XElement el)
-               {
-                       return GetContainingType (el) == "interface";
-               }
-
-               public XElement Source { get; set; }
-
-               public virtual bool Find (XElement e)
-               {
-                       return e.GetAttribute ("name") == Source.GetAttribute ("name");
-               }
-
-               XElement Find (IEnumerable<XElement> target)
-               {
-                       return State.Lax ? target.FirstOrDefault (Find) : target.SingleOrDefault (Find);
-               }
-
-               public override void Compare (IEnumerable<XElement> source, IEnumerable<XElement> target)
-               {
-                       removed.Clear ();
-                       modified.Clear ();
-
-                       foreach (var s in source) {
-                               SetContext (s);
-                               Source = s;
-                               var t = Find (target);
-                               if (t == null) {
-                                       // not in target, it was removed
-                                       removed.Add (s);
-                               } else {
-                                       t.Remove ();
-                                       // possibly modified
-                                       if (Equals (s, t, modified))
-                                               continue;
-
-                                       Modified (s, t, modified);
-                               }
-                       }
-                       // delayed, that way we show "Modified", "Added" and then "Removed"
-                       Remove (removed);
-
-                       Modify (modified);
-
-                       // remaining == newly added in target
-                       Add (target);
-               }
-
-               void Add (IEnumerable<XElement> elements)
-               {
-                       bool a = false;
-                       foreach (var item in elements) {
-                               SetContext (item);
-                               if (State.IgnoreAdded.Any (re => re.IsMatch (GetDescription (item))))
-                                       continue;
-                               if (!a) {
-                                       BeforeAdding (elements);
-                                       a = true;
-                               }
-                               Added (item, false);
-                       }
-                       if (a)
-                               AfterAdding ();
-               }
-
-               void Modify (ApiChanges modified)
-               {
-                       foreach (var changes in modified) {
-                               Output.WriteLine ("<p>{0}:</p>", changes.Key);
-                               Output.WriteLine ("<pre>");
-                               foreach (var element in changes.Value) {
-                                       Output.Write ("<div {0}>", element.Breaking ? "data-is-breaking" : "data-is-non-breaking");
-                                       foreach (var line in element.Member.ToString ().Split ('\n'))
-                                               Output.WriteLine ("\t{0}", line);
-                                       Output.Write ("</div>");
-
-                               }
-                               Output.WriteLine ("</pre>");
-                       }
-               }
-
-               void Remove (IEnumerable<XElement> elements)
-               {
-                       bool r = false;
-                       foreach (var item in elements) {
-                               if (State.IgnoreRemoved.Any (re => re.IsMatch (GetDescription (item))))
-                                       continue;
-                               SetContext (item);
-                               if (!r) {
-                                       BeforeRemoving (elements);
-                                       r = true;
-                               }
-                               Removed (item);
-                       }
-                       if (r)
-                               AfterRemoving ();
-               }
-                       
-               public abstract string GetDescription (XElement e);
-
-               protected StringBuilder GetObsoleteMessage (XElement e)
-               {
-                       var sb = new StringBuilder ();
-                       string o = e.GetObsoleteMessage ();
-                       if (o != null) {
-                               sb.Append ("[Obsolete");
-                               if (o.Length > 0)
-                                       sb.Append (" (\"").Append (o).Append ("\")");
-                               sb.AppendLine ("]");
-                               for (int i = 0; i < State.Indent + 1; i++)
-                                       sb.Append ('\t');
-                       }
-                       return sb;
-               }
-
-               public override bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       RenderAttributes (source, target, changes);
-
-                       // We don't want to compare attributes.
-                       RemoveAttributes (source);
-                       RemoveAttributes (target);
-
-                       return base.Equals (source, target, changes);
-               }
-
-               public virtual void BeforeAdding (IEnumerable<XElement> list)
-               {
-                       first = true;
-                       Output.WriteLine ("<div>");
-                       Output.WriteLine ("<p>Added {0}:</p>", list.Count () > 1 ? GroupName : ElementName);
-                       Output.WriteLine ("<pre>");
-               }
-
-               public override void Added (XElement target, bool wasParentAdded)
-               {
-                       var o = GetObsoleteMessage (target);
-                       if (!first && (o.Length > 0))
-                               Output.WriteLine ();
-                       Indent ();
-                       bool isInterfaceBreakingChange = !wasParentAdded && IsInInterface (target);
-                       Output.Write ("\t<span class='added added-{0} {1}' {2}>", ElementName, isInterfaceBreakingChange ? "breaking" : string.Empty, isInterfaceBreakingChange ? "data-is-breaking" : "data-is-non-breaking");
-                       Output.Write ("{0}{1}", o, GetDescription (target));
-                       Output.WriteLine ("</span>");
-                       first = false;
-               }
-
-               public virtual void AfterAdding ()
-               {
-                       Output.WriteLine ("</pre>");
-                       Output.WriteLine ("</div>");
-               }
-
-               public override void Modified (XElement source, XElement target, ApiChanges change)
-               {
-               }
-
-               public virtual void BeforeRemoving (IEnumerable<XElement> list)
-               {
-                       first = true;
-                       Output.WriteLine ("<p>Removed {0}:</p>\n", list.Count () > 1 ? GroupName : ElementName);
-                       Output.WriteLine ("<pre>");
-               }
-
-               public override void Removed (XElement source)
-               {
-                       var o = GetObsoleteMessage (source);
-                       if (!first && (o.Length > 0))
-                               Output.WriteLine ();
-
-                       bool is_breaking = IsBreakingRemoval (source);
-
-                       Indent ();
-                       Output.Write ("\t<span class='removed removed-{0} {2}' {1}>", ElementName, is_breaking ? "data-is-breaking" : "data-is-non-breaking", is_breaking ? "breaking" : string.Empty);
-                       Output.Write ("{0}{1}", o, GetDescription (source));
-                       Output.WriteLine ("</span>");
-                       first = false;
-               }
-
-               public virtual void AfterRemoving ()
-               {
-                       Output.WriteLine ("</pre>");;
-               }
-
-               string RenderGenericParameter (XElement gp)
-               {
-                       var sb = new StringBuilder ();
-                       sb.Append (gp.GetTypeName ("name"));
-
-                       var constraints = gp.DescendantList ("generic-parameter-constraints", "generic-parameter-constraint");
-                       if (constraints != null && constraints.Count > 0) {
-                               sb.Append (" : ");
-                               for (int i = 0; i < constraints.Count; i++) {
-                                       if (i > 0)
-                                               sb.Append (", ");
-                                       sb.Append (constraints [i].GetTypeName ("name"));
-                               }
-                       }
-                       return sb.ToString ();
-               }
-
-               protected void RenderGenericParameters (XElement source, XElement target, ApiChange change)
-               {
-                       var src = source.DescendantList ("generic-parameters", "generic-parameter");
-                       var tgt = target.DescendantList ("generic-parameters", "generic-parameter");
-                       var srcCount = src == null ? 0 : src.Count;
-                       var tgtCount = tgt == null ? 0 : tgt.Count;
-
-                       if (srcCount == 0 && tgtCount == 0)
-                               return;
-
-                       change.Append ("&lt;");
-                       for (int i = 0; i < Math.Max (srcCount, tgtCount); i++) {
-                               if (i > 0)
-                                       change.Append (", ");
-                               if (i >= srcCount) {
-                                       change.AppendAdded (RenderGenericParameter (tgt [i]), true);
-                               } else if (i >= tgtCount) {
-                                       change.AppendRemoved (RenderGenericParameter (src [i]), true);
-                               } else {
-                                       var srcName = RenderGenericParameter (src [i]);
-                                       var tgtName = RenderGenericParameter (tgt [i]);
-
-                                       if (srcName != tgtName) {
-                                               change.AppendModified (srcName, tgtName, true);
-                                       } else {
-                                               change.Append (srcName);
-                                       }
-                                       }
-                               }
-                       change.Append ("&gt;");
-               }
-
-               protected string FormatValue (string type, string value)
-               {
-                       if (value == null)
-                               return "null";
-
-                       if (type == "string")
-                               return "\"" + value + "\"";
-                       else if (type == "bool") {
-                               switch (value) {
-                               case "True":
-                                       return "true";
-                               case "False":
-                                       return "false";
-                               default:
-                                       return value;
-                               }
-                       }
-
-                       return value;
-               }
-
-               protected void RenderParameters (XElement source, XElement target, ApiChange change)
-               {
-                       var src = source.DescendantList ("parameters", "parameter");
-                       var tgt = target.DescendantList ("parameters", "parameter");
-                       var srcCount = src == null ? 0 : src.Count;
-                       var tgtCount = tgt == null ? 0 : tgt.Count;
-
-                       change.Append (" (");
-                       for (int i = 0; i < Math.Max (srcCount, tgtCount); i++) {
-                               if (i > 0)
-                                       change.Append (", ");
-
-                               if (i >= srcCount) {
-                                       change.AppendAdded (tgt [i].GetTypeName ("type") + " " + tgt [i].GetAttribute ("name"), true);
-                               } else if (i >= tgtCount) {
-                                       change.AppendRemoved (src [i].GetTypeName ("type") + " " + src [i].GetAttribute ("name"), true);
-                               } else {
-                                       var paramSourceType = src [i].GetTypeName ("type");
-                                       var paramTargetType = tgt [i].GetTypeName ("type");
-
-                                       var paramSourceName = src [i].GetAttribute ("name");
-                                       var paramTargetName = tgt [i].GetAttribute ("name");
-
-                                       if (paramSourceType != paramTargetType) {
-                                               change.AppendModified (paramSourceType, paramTargetType, true);
-                                       } else {
-                                               change.Append (paramSourceType);
-                                       }
-                                       change.Append (" ");
-                                       if (paramSourceName != paramTargetName) {
-                                               change.AppendModified (paramSourceName, paramTargetName, false);
-                                       } else {
-                                               change.Append (paramSourceName);
-                                       }
-
-                                       var optSource = src [i].Attribute ("optional");
-                                       var optTarget = tgt [i].Attribute ("optional");
-                                       var srcValue = FormatValue (paramSourceType, src [i].GetAttribute ("defaultValue"));
-                                       var tgtValue = FormatValue (paramTargetType, tgt [i].GetAttribute ("defaultValue"));
-
-                                       if (optSource != null) {
-                                               if (optTarget != null) {
-                                                       change.Append (" = ");
-                                                       if (srcValue != tgtValue) {
-                                                               change.AppendModified (srcValue, tgtValue, false);
-                                                       } else {
-                                                               change.Append (tgtValue);
-                                                       }
-                                               } else {
-                                                       change.AppendRemoved (" = " + srcValue);
-                                               }
-                                       } else {
-                                               if (optTarget != null)
-                                                       change.AppendAdded (" = " + tgtValue);
-                                       }
-                               }
-                       }
-
-                       change.Append (")");
-
-                       // Ignore any parameter name changes if requested.
-                       if (State.IgnoreParameterNameChanges && !change.Breaking) {
-                               change.AnyChange = false;
-                               change.HasIgnoredChanges = true;
-                       }
-               }
-
-               void RenderVTable (MethodAttributes source, MethodAttributes target, ApiChange change)
-               {
-                       var srcAbstract = (source & MethodAttributes.Abstract) == MethodAttributes.Abstract;
-                       var tgtAbstract = (target & MethodAttributes.Abstract) == MethodAttributes.Abstract;
-                       var srcFinal = (source & MethodAttributes.Final) == MethodAttributes.Final;
-                       var tgtFinal = (target & MethodAttributes.Final) == MethodAttributes.Final;
-                       var srcVirtual = (source & MethodAttributes.Virtual) == MethodAttributes.Virtual;
-                       var tgtVirtual = (target & MethodAttributes.Virtual) == MethodAttributes.Virtual;
-                       var srcOverride = (source & MethodAttributes.VtableLayoutMask) != MethodAttributes.NewSlot;
-                       var tgtOverride = (target & MethodAttributes.VtableLayoutMask) != MethodAttributes.NewSlot;
-
-                       var srcWord = srcVirtual ? (srcOverride ? "override" : "virtual") : string.Empty;
-                       var tgtWord = tgtVirtual ? (tgtOverride ? "override" : "virtual") : string.Empty;
-                       var breaking = srcWord.Length > 0 && tgtWord.Length == 0;
-
-                       if (srcAbstract) {
-                               if (tgtAbstract) {
-                                       change.Append ("abstract ");
-                               } else if (tgtVirtual) {
-                                       change.AppendModified ("abstract", tgtWord, false).Append (" ");
-                               } else {
-                                       change.AppendRemoved ("abstract").Append (" ");
-                               }
-                       } else {
-                               if (tgtAbstract) {
-                                       change.AppendAdded ("abstract", true).Append (" ");
-                               } else if (srcWord != tgtWord) {
-                                       if (!tgtFinal)
-                                               change.AppendModified (srcWord, tgtWord, breaking).Append (" ");
-                               } else if (tgtWord.Length > 0) {
-                                       change.Append (tgtWord).Append (" ");
-                               } else if (srcWord.Length > 0) {
-                                       change.AppendRemoved (srcWord, breaking).Append (" ");
-                               }
-                       }
-
-                       if (srcFinal) {
-                               if (tgtFinal) {
-                                       change.Append ("final ");
-                               } else {
-                                       change.AppendRemoved ("final", false).Append (" "); // removing 'final' is not a breaking change.
-                               }
-                       } else {
-                               if (tgtFinal && srcVirtual) {
-                                       change.AppendModified ("virtual", "final", true).Append (" "); // adding 'final' is a breaking change if the member was virtual
-                               }
-                       }
-
-                       if (!srcVirtual && !srcFinal && tgtVirtual && tgtFinal) {
-                               // existing member implements a member from a new interface
-                               // this would show up as 'virtual final', which is redundant, so show nothing at all.
-                               change.HasIgnoredChanges = true;
-                       }
-
-                       // Ignore non-breaking virtual changes.
-                       if (State.IgnoreVirtualChanges && !change.Breaking) {
-                               change.AnyChange = false;
-                               change.HasIgnoredChanges = true;
-                       }
-
-                       var tgtSecurity = (source & MethodAttributes.HasSecurity) == MethodAttributes.HasSecurity;
-                       var srcSecurity = (target & MethodAttributes.HasSecurity) == MethodAttributes.HasSecurity;
-
-                       if (tgtSecurity != srcSecurity)
-                               change.HasIgnoredChanges = true;
-
-                       var srcPInvoke = (source & MethodAttributes.PinvokeImpl) == MethodAttributes.PinvokeImpl;
-                       var tgtPInvoke = (target & MethodAttributes.PinvokeImpl) == MethodAttributes.PinvokeImpl;
-                       if (srcPInvoke != tgtPInvoke)
-                               change.HasIgnoredChanges = true;
-               }
-
-               protected string GetVisibility (MethodAttributes attr)
-               {
-                       switch (attr) {
-                       case MethodAttributes.Private:
-                       case MethodAttributes.PrivateScope:
-                               return "private";
-                       case MethodAttributes.Assembly:
-                               return "internal";
-                       case MethodAttributes.FamANDAssem:
-                               return "private internal";
-                       case MethodAttributes.FamORAssem:
-                               return "protected"; // customers don't care about 'internal';
-                       case MethodAttributes.Family:
-                               return "protected";
-                       case MethodAttributes.Public:
-                               return "public";
-                       default:
-                               throw new NotImplementedException ();
-                       }
-               }
-
-               protected void RenderVisibility (MethodAttributes source, MethodAttributes target, ApiChange diff)
-               {
-                       source = source & MethodAttributes.MemberAccessMask;
-                       target = target & MethodAttributes.MemberAccessMask;
-
-                       if (source == target) {
-                               diff.Append (GetVisibility (target));
-                       } else {
-                               var breaking = false;
-                               switch (source) {
-                               case MethodAttributes.Private:
-                               case MethodAttributes.Assembly:
-                               case MethodAttributes.FamANDAssem:
-                                       break; // these are not publicly visible, thus not breaking
-                               case MethodAttributes.FamORAssem:
-                               case MethodAttributes.Family:
-                                       switch (target) {
-                                       case MethodAttributes.Public:
-                                               // to public is not a breaking change
-                                               break;
-                                       case MethodAttributes.Family:
-                                       case MethodAttributes.FamORAssem:
-                                               // not a breaking change, but should still show up in diff
-                                               break;
-                                       default:
-                                               // anything else is a breaking change
-                                               breaking = true;
-                                               break;
-                                       }
-                                       break;
-                               case MethodAttributes.Public:
-                               default:
-                                       // any change from public is breaking.
-                                       breaking = true;
-                                       break;
-                               }
-
-                               diff.AppendModified (GetVisibility (source), GetVisibility (target), breaking);
-                       }
-                       diff.Append (" ");
-               }
-
-               protected void RenderStatic (MethodAttributes src, MethodAttributes tgt, ApiChange diff)
-               {
-                       var srcStatic = (src & MethodAttributes.Static) == MethodAttributes.Static;
-                       var tgtStatic = (tgt & MethodAttributes.Static) == MethodAttributes.Static;
-
-                       if (srcStatic != tgtStatic) {
-                               if (srcStatic) {
-                                       diff.AppendRemoved ("static", true).Append (" ");
-                               } else {
-                                       diff.AppendAdded ("static", true).Append (" ");
-                               }
-                       }
-               }
-
-               protected void RenderMethodAttributes (MethodAttributes src, MethodAttributes tgt, ApiChange diff)
-               {
-                       RenderStatic (src, tgt, diff);
-                       RenderVisibility (src & MethodAttributes.MemberAccessMask, tgt & MethodAttributes.MemberAccessMask, diff);
-                       RenderVTable (src, tgt, diff);
-               }
-
-               protected void RenderMethodAttributes (XElement source, XElement target, ApiChange diff)
-               {
-                       RenderMethodAttributes (source.GetMethodAttributes (), target.GetMethodAttributes (), diff);
-               }
-
-               protected void RemoveAttributes (XElement element)
-               {
-                       var srcAttributes = element.Element ("attributes");
-                       if (srcAttributes != null)
-                               srcAttributes.Remove ();
-
-                       foreach (var el in element.Elements ())
-                               RemoveAttributes (el);
-               }
-
-               protected void RenderAttributes (XElement source, XElement target, ApiChanges changes)
-               {
-                       var srcObsolete = source.GetObsoleteMessage ();
-                       var tgtObsolete = target.GetObsoleteMessage ();
-
-                       if (srcObsolete == tgtObsolete)
-                               return; // nothing changed
-
-                       if (srcObsolete == null) {
-                               if (tgtObsolete == null)
-                                       return; // neither is obsolete
-                               var change = new ApiChange ();
-                               change.Header = "Obsoleted " + GroupName;
-                               change.Append (string.Format ("<span class='obsolete obsolete-{0}' data-is-non-breaking>", ElementName));
-                               change.Append ("[Obsolete (");
-                               if (tgtObsolete != string.Empty)
-                                       change.Append ("\"").Append (tgtObsolete).Append ("\"");
-                               change.Append (")]\n");
-                               change.Append (GetDescription (target));
-                               change.Append ("</span>");
-                               change.AnyChange = true;
-                               changes.Add (source, target, change);
-                       } else if (tgtObsolete == null) {
-                               // Made non-obsolete. Do we care to report this?
-                       } else {
-                               // Obsolete message changed. Do we care to report this?
-                       }
-               }
-
-               protected void RenderName (XElement source, XElement target, ApiChange change)
-               {
-                       var name = target.GetAttribute ("name");
-                       // show the constructor as it would be defined in C#
-                       name = name.Replace (".ctor", State.Type);
-
-                       var p = name.IndexOf ('(');
-                       if (p >= 0)
-                               name = name.Substring (0, p);
-
-                       change.Append (name);
-               }
-
-       }
-}
diff --git a/mcs/tools/corcompare/mono-api-html/MethodComparer.cs b/mcs/tools/corcompare/mono-api-html/MethodComparer.cs
deleted file mode 100644 (file)
index 4c893e7..0000000
+++ /dev/null
@@ -1,77 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Linq;
-using System.Reflection;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class MethodComparer : ConstructorComparer {
-
-               public override string GroupName {
-                       get { return "methods"; }
-               }
-
-               public override string ElementName {
-                       get { return "method"; }
-               }
-
-               // operators have identical names but vary by return types
-               public override bool Find (XElement e)
-               {
-                       if (e.GetAttribute ("name") != Source.GetAttribute ("name"))
-                               return false;
-
-                       if (e.GetAttribute ("returntype") != Source.GetAttribute ("returntype"))
-                               return false;
-
-                       var eGP = e.Element ("generic-parameters");
-                       var sGP = Source.Element ("generic-parameters");
-
-                       if (eGP == null && sGP == null)
-                               return true;
-                       else if (eGP == null ^ sGP == null)
-                               return false;
-                       else {
-                               var eGPs = eGP.Elements ("generic-parameter");
-                               var sGPs = sGP.Elements ("generic-parameter");
-                               return eGPs.Count () == sGPs.Count ();
-                       }
-               }
-
-               protected override bool IsBreakingRemoval (XElement e)
-               {
-                       // Removing virtual methods that override another method is not a breaking change.
-                       var is_override = e.Attribute ("is-override");
-                       if (is_override != null)
-                               return is_override.Value != "true";
-                       
-                       return true; // all other removals are breaking changes
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/NamespaceComparer.cs b/mcs/tools/corcompare/mono-api-html/NamespaceComparer.cs
deleted file mode 100644 (file)
index 063e34e..0000000
+++ /dev/null
@@ -1,104 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.IO;
-using System.Linq;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class NamespaceComparer : Comparer {
-
-               ClassComparer comparer;
-
-               public NamespaceComparer ()
-               {
-                       comparer =  new ClassComparer ();
-               }
-
-               public void Compare (XElement source, XElement target)
-               {
-                       var s = source.Element ("namespaces");
-                       var t = target.Element ("namespaces");
-                       if (XNode.DeepEquals (s, t))
-                               return;
-                       Compare (s.Elements ("namespace"), t.Elements ("namespace"));
-               }
-
-               public override void SetContext (XElement current)
-               {
-                       State.Namespace = current.Attribute ("name").Value;
-               }
-
-               public override void Added (XElement target, bool wasParentAdded)
-               {
-                       string name = target.Attribute ("name").Value;
-                       if (State.IgnoreNew.Any (re => re.IsMatch (name)))
-                               return;
-
-                       Output.WriteLine ("<!-- start namespace {0} --> <div> ", name);
-                       Output.WriteLine ("<h2>New Namespace {0}</h2>", name);
-                       Output.WriteLine ();
-                       // list all new types
-                       foreach (var addedType in target.Element ("classes").Elements ("class"))
-                               comparer.Added (addedType, true);
-                       Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
-                       Output.WriteLine ();
-               }
-
-               public override void Modified (XElement source, XElement target, ApiChanges differences)
-               {
-                       var output = Output;
-                       State.Output = new StringWriter ();
-                       comparer.Compare (source, target);
-
-                       var s = Output.ToString ();
-                       State.Output = output;
-                       if (s.Length > 0) {
-                               var name = target.Attribute ("name").Value;
-                               Output.WriteLine ("<!-- start namespace {0} --> <div> ", name);
-                               Output.WriteLine ("<h2>Namespace {0}</h2>", name);
-                               Output.WriteLine (s);
-                               Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
-                       }
-               }
-
-               public override void Removed (XElement source)
-               {
-                       var name = source.Attribute ("name").Value;
-                       Output.WriteLine ("<!-- start namespace {0} --> <div>", name);
-                       Output.WriteLine ("<h2>Removed Namespace {0}</h2>", name);
-                       Output.WriteLine ();
-                       // list all removed types
-                       foreach (var removedType in source.Element ("classes").Elements ("class"))
-                               comparer.Removed (removedType);
-                       Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
-                       Output.WriteLine ();
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/PropertyComparer.cs b/mcs/tools/corcompare/mono-api-html/PropertyComparer.cs
deleted file mode 100644 (file)
index f51dd23..0000000
+++ /dev/null
@@ -1,254 +0,0 @@
-// 
-// Authors
-//    Sebastien Pouliot  <sebastien@xamarin.com>
-//
-// Copyright 2013 Xamarin Inc. http://www.xamarin.com
-// 
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-//
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-//
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
-
-using System;
-using System.Collections.Generic;
-using System.Reflection;
-using System.Text;
-using System.Xml.Linq;
-
-namespace Xamarin.ApiDiff {
-
-       public class PropertyComparer : MemberComparer {
-
-               public override string GroupName {
-                       get { return "properties"; }
-               }
-
-               public override string ElementName {
-                       get { return "property"; }
-               }
-
-               public override bool Find (XElement e)
-               {
-                       if (!base.Find (e))
-                               return false;
-                       // the same Item (indexer) property can have different parameters
-                       return e.GetAttribute ("params") == Source.GetAttribute ("params");
-               }
-
-               void GetAccessors (XElement element, out XElement getter, out XElement setter)
-               {
-                       var methods = element.Element ("methods");
-
-                       getter = null;
-                       setter = null;
-
-                       if (methods == null)
-                               return;
-                               
-                       foreach (var m in methods.Elements ("method")) {
-                               var n = m.GetAttribute ("name");
-                               if (n.StartsWith ("get_", StringComparison.Ordinal)) {
-                                       getter = m;
-                               } else if (n.StartsWith ("set_", StringComparison.Ordinal)) {
-                                       setter = m;
-                               }
-                       }
-               }
-
-               MethodAttributes GetMethodAttributes (XElement getter, XElement setter)
-               {
-                       if (getter == null)
-                               return setter.GetMethodAttributes ();
-                       else if (setter == null)
-                               return getter.GetMethodAttributes ();
-
-                       var gAttr = getter.GetMethodAttributes ();
-                       var sAttr = setter.GetMethodAttributes ();
-                       var g = gAttr & MethodAttributes.MemberAccessMask;
-                       var s = sAttr & MethodAttributes.MemberAccessMask;
-                       // Visibility is ordered numerically (higher value = more visible).
-                       // We want the most visible.
-                       var visibility = (MethodAttributes) Math.Max ((int) g, (int) s);
-                       // Do a bitwise or with the rest of the flags
-                       var g_no_visibility = gAttr & ~MethodAttributes.MemberAccessMask;
-                       var s_no_visibility = sAttr & ~MethodAttributes.MemberAccessMask;
-                       return g_no_visibility | s_no_visibility | visibility;
-               }
-
-               void RenderPropertyType (XElement source, XElement target, ApiChange change)
-               {
-                       var srcType = source.GetTypeName ("ptype");
-                       var tgtType = target.GetTypeName ("ptype");
-
-                       if (srcType == tgtType) {
-                               change.Append (tgtType);
-                       } else {
-                               change.AppendModified (srcType, tgtType, true);
-                       }
-                       change.Append (" ");
-               }
-
-               void RenderAccessors (XElement srcGetter, XElement tgtGetter, XElement srcSetter, XElement tgtSetter, ApiChange change)
-               {
-                       // FIXME: this doesn't render changes in the accessor visibility (a protected setter can become public for instance).
-                       change.Append (" {");
-                       if (tgtGetter != null) {
-                               if (srcGetter != null) {
-                                       change.Append (" ").Append ("get;");
-                               } else {
-                                       change.Append (" ").AppendAdded ("get;");
-                               }
-                       } else if (srcGetter != null) {
-                               change.Append (" ").AppendRemoved ("get;");
-                       }
-
-                       if (tgtSetter != null) {
-                               if (srcSetter != null) {
-                                       change.Append (" ").Append ("set;");
-                               } else {
-                                       change.Append (" ").AppendAdded ("set;");
-                               }
-                       } else if (srcSetter != null) {
-                               change.Append (" ").AppendRemoved ("set;");
-                       }
-
-                       change.Append (" }");
-
-                       // Ignore added property setters if asked to
-                       if (srcSetter == null && tgtSetter != null && State.IgnoreAddedPropertySetters && !change.Breaking) {
-                               change.AnyChange = false;
-                               change.HasIgnoredChanges = true;
-                       }
-               }
-
-               void RenderIndexers (List<XElement> srcIndexers, List<XElement> tgtIndexers, ApiChange change)
-               {
-                       change.Append ("this [");
-                       for (int i = 0; i < srcIndexers.Count; i++) {
-                               var source = srcIndexers [i];
-                               var target = tgtIndexers [i];
-
-                               if (i > 0)
-                                       change.Append (", ");
-
-                               var srcType = source.GetTypeName ("type");
-                               var tgtType = target.GetTypeName ("type");
-                               if (srcType == tgtType) {
-                                       change.Append (tgtType);
-                               } else {
-                                       change.AppendModified (srcType, tgtType, true);
-                               }
-                               change.Append (" ");
-
-                               var srcName = source.GetAttribute ("name");
-                               var tgtName = target.GetAttribute ("name");
-                               if (srcName == tgtName) {
-                                       change.Append (tgtName);
-                               } else {
-                                       change.AppendModified (srcName, tgtName, true);
-                               }
-                       }
-                       change.Append ("]");
-               }
-
-               public override bool Equals (XElement source, XElement target, ApiChanges changes)
-               {
-                       if (base.Equals (source, target, changes))
-                               return true;
-
-                       XElement srcGetter, srcSetter;
-                       XElement tgtGetter, tgtSetter;
-                       GetAccessors (source, out srcGetter, out srcSetter);
-                       GetAccessors (target, out tgtGetter, out tgtSetter);
-
-                       List<XElement> srcIndexers = null;
-                       List<XElement> tgtIndexers = null;
-                       bool isIndexer = false;
-                       if (srcGetter != null) {
-                               srcIndexers = srcGetter.DescendantList ("parameters", "parameter");
-                               tgtIndexers = tgtGetter.DescendantList ("parameters", "parameter");
-                               isIndexer = srcIndexers != null && srcIndexers.Count > 0;
-                       }
-
-                       var change = new ApiChange ();
-                       change.Header = "Modified " + GroupName;
-                       RenderMethodAttributes (GetMethodAttributes (srcGetter, srcSetter), GetMethodAttributes (tgtGetter, tgtSetter), change);
-                       RenderPropertyType (source, target, change);
-                       if (isIndexer) {
-                               RenderIndexers (srcIndexers, tgtIndexers, change);
-                       } else {
-                               RenderName (source, target, change);
-                       }
-                       RenderGenericParameters (source, target, change);
-                       RenderAccessors (srcGetter, tgtGetter, srcSetter, tgtSetter, change);
-
-                       changes.Add (source, target, change);
-
-                       return false;
-               }
-
-               void GetProperties (XElement e, out bool @virtual, out bool @override, out bool @static, out bool getter, out bool setter, out bool family)
-               {
-                       @virtual = @override = @static = getter = setter = family = false;
-
-                       var methods = e.Element ("methods");
-                       if (methods != null) {
-                               foreach (var m in methods.Elements ("method")) {
-                                       @virtual |= m.IsTrue ("virtual");
-                                       @static |= m.IsTrue ("static");
-                                       var n = m.GetAttribute ("name");
-                                       getter |= n.StartsWith ("get_", StringComparison.Ordinal);
-                                       setter |= n.StartsWith ("set_", StringComparison.Ordinal);
-                                       var attribs = (MethodAttributes) Int32.Parse (m.GetAttribute ("attrib"));
-                                       family = ((attribs & MethodAttributes.Public) != MethodAttributes.Public);
-                                       @override |= (attribs & MethodAttributes.NewSlot) == 0;
-                               }
-                       }
-               }
-
-               public override string GetDescription (XElement e)
-               {
-                       string name = e.Attribute ("name").Value;
-                       string ptype = e.GetTypeName ("ptype");
-
-                       bool virt = false;
-                       bool over = false;
-                       bool stat = false;
-                       bool getter = false;
-                       bool setter = false;
-                       bool family = false;
-                       GetProperties (e, out virt, out over, out stat, out getter, out setter, out family);
-
-                       var sb = new StringBuilder ();
-
-                       sb.Append (family ? "protected " : "public ");
-                       if (virt && !State.IgnoreVirtualChanges)
-                               sb.Append (over ? "override " : "virtual ");
-                       else if (stat)
-                               sb.Append ("static ");
-                       sb.Append (ptype).Append (' ').Append (name).Append (" { ");
-                       if (getter)
-                               sb.Append ("get; ");
-                       if (setter)
-                               sb.Append ("set; ");
-                       sb.Append ("}");
-
-                       return sb.ToString ();
-               }
-       }
-}
\ No newline at end of file
diff --git a/mcs/tools/corcompare/mono-api-html/mono-api-html.csproj b/mcs/tools/corcompare/mono-api-html/mono-api-html.csproj
deleted file mode 100644 (file)
index 6ac0f24..0000000
+++ /dev/null
@@ -1,57 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
-  <PropertyGroup>
-    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
-    <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
-    <ProductVersion>8.0.30703</ProductVersion>
-    <SchemaVersion>2.0</SchemaVersion>
-    <ProjectGuid>{D25986E2-7A41-4966-A26D-5614BAC7B8A7}</ProjectGuid>
-    <OutputType>Exe</OutputType>
-    <RootNamespace>Xamarin.ApiDiff</RootNamespace>
-    <AssemblyName>mono-api-html</AssemblyName>
-  </PropertyGroup>
-  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
-    <DebugSymbols>true</DebugSymbols>
-    <DebugType>full</DebugType>
-    <Optimize>false</Optimize>
-    <OutputPath>bin\Debug</OutputPath>
-    <DefineConstants>DEBUG;</DefineConstants>
-    <ErrorReport>prompt</ErrorReport>
-    <WarningLevel>4</WarningLevel>
-    <ConsolePause>false</ConsolePause>
-  </PropertyGroup>
-  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
-    <DebugType>full</DebugType>
-    <Optimize>true</Optimize>
-    <OutputPath>bin\Release</OutputPath>
-    <ErrorReport>prompt</ErrorReport>
-    <WarningLevel>4</WarningLevel>
-    <Externalconsole>true</Externalconsole>
-  </PropertyGroup>
-  <ItemGroup>
-    <Reference Include="System" />
-    <Reference Include="System.Xml.Linq" />
-    <Reference Include="System.Xml" />
-    <Reference Include="System.Core" />
-  </ItemGroup>
-  <ItemGroup>
-    <Compile Include="Helpers.cs" />
-    <Compile Include="InterfaceComparer.cs" />
-    <Compile Include="NamespaceComparer.cs" />
-    <Compile Include="MemberComparer.cs" />
-    <Compile Include="FieldComparer.cs" />
-    <Compile Include="PropertyComparer.cs" />
-    <Compile Include="EventComparer.cs" />
-    <Compile Include="MethodComparer.cs" />
-    <Compile Include="ConstructorComparer.cs" />
-    <Compile Include="Comparer.cs" />
-    <Compile Include="AssemblyComparer.cs" />
-    <Compile Include="ClassComparer.cs" />
-    <Compile Include="ApiDiff.cs" />
-    <Compile Include="..\..\..\class\Mono.Options\Mono.Options\Options.cs">
-      <Link>Options.cs</Link>
-    </Compile>
-    <Compile Include="ApiChange.cs" />
-  </ItemGroup>
-  <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
-</Project>
diff --git a/mcs/tools/corcompare/mono-api-info.exe.sources b/mcs/tools/corcompare/mono-api-info.exe.sources
new file mode 100644 (file)
index 0000000..9ae6cd0
--- /dev/null
@@ -0,0 +1,5 @@
+AssemblyResolver.cs
+Util.cs
+WellFormedXmlWriter.cs
+mono-api-info.cs
+../../class/Mono.Options/Mono.Options/Options.cs
index 7a03be5761c6aadb0b99e9f4e2711e2d8bc4d919..1c3a80355eeddb2acf1b3c69ad375dc43d830219 100644 (file)
@@ -6,7 +6,8 @@ include ../../build/rules.make
 
 // 3021: CLS attribute not needed since assembly is not CLS compliant
 NOWARNS = -nowarn:3021
-LOCAL_MCS_FLAGS = -r:$(topdir)/class/lib/$(PROFILE)/Mono.CSharp.dll -r:$(topdir)/class/lib/$(PROFILE)/Mono.Posix.dll -r:Mono.Management.dll -r:System.dll -unsafe $(NOWARNS)
+LOCAL_MCS_FLAGS = -unsafe $(NOWARNS)
+LIB_REFS = Mono.CSharp Mono.Posix Mono.Management System 
 
 PROGRAM = csharp.exe
 
index cfc68da231092773d7d28b5b1f70db7f1d977266..c186b8e74a2a58b5d3fa99ad212257135ea682b2 100644 (file)
@@ -2,7 +2,7 @@ thisdir = tools/culevel
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Xml.dll
+LIB_REFS = System System.Xml
 PROGRAM = culevel.exe
 
 CLEAN_FILES = culevel.exe culevel.exe.mdb
index 12869f51ecffda24935dcdf5f4e3b5c3864e982a..77721fa1df1151e137011b04e547c2d3c056e696 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/disco
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:System.Web.Services.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml System.Web.Services System
 PROGRAM = disco.exe
 
 include ../../build/executable.make
index 48e0059409c292f10f66beaf1f49b043c599b799..14f8c2906b980e0defecd1b062d16fd2c74ec58b 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/dtd2rng
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:Commons.Xml.Relaxng.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml Commons.Xml.Relaxng
 PROGRAM = dtd2rng.exe
 
 include ../../build/executable.make
index 80431266b27582058736a48796b23a9f4332305d..fa500c8c679cd0e18ec0a47f30d322e1079e415b 100755 (executable)
@@ -2,7 +2,8 @@ thisdir = tools/dtd2xsd
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml
 PROGRAM = dtd2xsd.exe
 
 include ../../build/executable.make
index 878830f124886cd0723c47115b443a2f065003ac..f98314ecec7afb9db0957bb70edde80431c647b9 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/gacutil
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:Mono.Security.dll -unsafe
+LIB_REFS = Mono.Security
+LOCAL_MCS_FLAGS = -unsafe
 
 PROGRAM = gacutil.exe
 
index 3446b6f74c0afdbc912a571af8cb900b089945f8..13f686e22c64ec5dadc09c136838db3ed7c74a43 100644 (file)
@@ -324,6 +324,11 @@ namespace Mono.Tools {
 
                        Copy (name, asmb_path, true);
 
+                       var name_pdb = Path.ChangeExtension (name, ".pdb");
+                       if (File.Exists (name_pdb)) {
+                               Copy (name_pdb, Path.ChangeExtension (asmb_path, ".pdb"), true);
+                       }
+
                        foreach (string ext in siblings) {
                                string sibling = String.Concat (name, ext);
                                if (File.Exists (sibling))
@@ -356,9 +361,23 @@ namespace Mono.Tools {
                                        string pkg_path = AbsoluteToRelativePath (ref_dir, pkg_path_abs);
                                        symlink (pkg_path, ref_path);
 
+                                       var pdb_pkg_path = Path.ChangeExtension (pkg_path, ".pdb");
+                                       var pdb_ref_path = Path.ChangeExtension (ref_path, ".pdb");
+
+                                       if (File.Exists (pdb_pkg_path)) {
+                                               symlink (pdb_pkg_path, pdb_ref_path);
+                                       } else {
+                                               try {
+                                                       File.Delete (pdb_ref_path);
+                                               } catch {
+                                                       // Ignore error, just delete files that should not be there.
+                                               }
+                                       }
+
                                        foreach (string ext in siblings) {
                                                string sibling = String.Concat (pkg_path, ext);
                                                string sref = String.Concat (ref_path, ext);
+
                                                if (File.Exists (sibling))
                                                        symlink (sibling, sref);
                                                else {
index 21b38e8fd3c77839f1e7c09c22d5c1d03757b527..71819a2eb5248b1cdff27957f75b0c2ef0d346f8 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/genxs
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml
 PROGRAM = genxs.exe
 
 include ../../build/executable.make
index 13ffb114c20ae90ec83b3f38f68a7ca1c182916f..f34409878c3704c9ca6d76d1d195ce409847362b 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/ictool
 SUBDIRS =
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml
 
 PROGRAM = ictool.exe
 EXTRA_DISTFILES = ictool-config.xml
index 6a6cb6fb544db6637da27823b0190bfdd1174d7e..1d0a78c83e06d3a62586fed60fa271de9adf34d0 100644 (file)
@@ -3,9 +3,9 @@ SUBDIRS =
 include ../../build/rules.make
 
 PROGRAM = ikdasm.exe
-
+LIB_REFS = System System.Core System.Security
 LOCAL_MCS_FLAGS = \
-       -d:NO_SYMBOL_WRITER /r:System.Security.dll /r:System.Core.dll /r:System.dll
+       -d:NO_SYMBOL_WRITER
 
 #EXTRA_DISTFILES = LICENSE
 
index c545a4630eb709aff273ca3c64311e0385af1189..e7f4401169feaa1252c91b4660b67879989fb673 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/installutil
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Configuration.Install.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Configuration.Install System
 
 PROGRAM = installutil.exe
 
index a5479c948ddc4bf6dc16582d74cdcf551970de08..3ba67fe0d8fd4f202d654b2efc5cd6c114e2a268 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/installvst
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml
 PROGRAM = installvst.exe
 
 include ../../build/executable.make
index d77c8ab6f73644033b12e156f2e7b0e1beadcf8c..905a75a488aa6ea5827e7a3cbb7d8892170ad8e3 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/lc
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Core.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System System.Core
 PROGRAM = lc.exe
 
 CLEAN_FILES = lc.exe lc.exe.mdb
index e68e7f6c39bd676345c56b3c8145120648aaf3ae..08a3fdc093a7dbcd9725f02eb1ace282edf12dfe 100644 (file)
@@ -4,6 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = linkeranalyzer.exe
 
-LOCAL_MCS_FLAGS = /r:System.dll /r:System.Xml.dll
+LIB_REFS = System System.Xml
+LOCAL_MCS_FLAGS =
 
 include ../../build/executable.make
index 63c5eb6adce769bff8c1b9107149ad02576bd708..3dd8398d2bcfad2456c4cf303d6cc2cd34666bf0 100644 (file)
@@ -2,10 +2,6 @@ thisdir = tools/linker
 SUBDIRS =
 include ../../build/rules.make
 
-PROGRAM_SNK = ../../class/mono.snk
-
-CECIL = $(topdir)/class/lib/$(PROFILE)/Mono.Cecil.dll
-
 RESOURCES = \
        Descriptors/mscorlib.xml        \
        Descriptors/System.xml          \
@@ -18,7 +14,8 @@ PROGRAM = monolinker.exe
 
 $(PROGRAM): $(RESOURCES)
 
-LOCAL_MCS_FLAGS = /r:$(CECIL) /r:System.Xml.dll /r:System.Core.dll /r:System.dll $(RESOURCES:%=-resource:%)
+LIB_REFS = System System.Core System.Xml Mono.Cecil
+LOCAL_MCS_FLAGS = $(RESOURCES:%=-resource:%)
 
 EXTRA_DISTFILES = $(RESOURCES)
 
index 0e99e810203cb39600c34ab5c6d2fc6c67ae4b35..74e61e3541c895af113ea346790d598269aa3ff8 100644 (file)
@@ -527,6 +527,7 @@ namespace Mono.Linker.Steps {
                        if (type.HasMethods) {
                                MarkMethodsIf (type.Methods, IsVirtualAndHasPreservedParent);
                                MarkMethodsIf (type.Methods, IsStaticConstructorPredicate);
+                               MarkMethodsIf (type.Methods, HasSerializationAttribute);
                        }
 
                        DoAdditionalTypeProcessing (type);
@@ -740,6 +741,25 @@ namespace Mono.Linker.Steps {
                        return method.IsConstructor && method.IsStatic;
                }
 
+               static bool HasSerializationAttribute (MethodDefinition method)
+               {
+                       if (!method.HasCustomAttributes)
+                               return false;
+                       foreach (var ca in method.CustomAttributes) {
+                               var cat = ca.AttributeType;
+                               if (cat.Namespace != "System.Runtime.Serialization")
+                                       continue;
+                               switch (cat.Name) {
+                               case "OnDeserializedAttribute":
+                               case "OnDeserializingAttribute":
+                               case "OnSerializedAttribute":
+                               case "OnSerializingAttribute":
+                                       return true;
+                               }
+                       }
+                       return false;
+               }
+
                static bool IsSerializable (TypeDefinition td)
                {
                        return (td.Attributes & TypeAttributes.Serializable) != 0;
index f7f8721adc130c0e0e46f926ff74fe2bb3cabe26..92fc95c91f12e5a9cb6264dbda65c233aba2ab30 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mconfig
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml System
 PROGRAM = mconfig.exe
 
 BUILT_SOURCES=Mono.MonoConfig/consts.cs
index 9647a44d52fdf3bc1b86f45a9b1feeba9cdf0d36..55d4012a13a2e633cd475f6e91b7e340d55b83bb 100644 (file)
@@ -4,9 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = mdbdump.exe
 
-LOCAL_MCS_FLAGS = \
-       /r:System.Xml.dll \
-       /r:Mono.Cecil.dll       \
-       /r:Mono.CompilerServices.SymbolWriter.dll
+LIB_REFS = Mono.Cecil System.Xml Mono.CompilerServices.SymbolWriter
+LOCAL_MCS_FLAGS =
 
 include ../../build/executable.make
index e0432ef90a798ad6d610903a14bba6d56bc06958..e0f6fe81956c8d31dcc2fda6fd1dabbec4db5658 100644 (file)
@@ -4,7 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = mdbrebase.exe
 
-LOCAL_MCS_FLAGS = /r:Mono.CompilerServices.SymbolWriter.dll /r:System.dll
-
+LIB_REFS = System Mono.CompilerServices.SymbolWriter
+LOCAL_MCS_FLAGS =
 
 include ../../build/executable.make
index 3fb309b227320e5b6d26830d56d7e35143adf14c..efb76cbf9e0dea90c21deeae424c932d5d57c504 100644 (file)
@@ -12,16 +12,10 @@ MDOC_COMMON_FLAGS = \
        /resource:Resources/msitomsx.xsl,msitomsx.xsl                               \
        /resource:Resources/overview.xsl,overview.xsl                               \
        /resource:Resources/stylesheet.xsl,stylesheet.xsl                           \
-       /r:System.Web.dll                                                           \
-       /r:System.Xml.Linq.dll                                                      \
-       /r:ICSharpCode.SharpZipLib.dll                                              \
-       /r:Mono.Cecil.dll \
-       /r:System.dll \
-       /r:System.Xml.dll \
-       /r:System.Core.dll
-
-LOCAL_MCS_FLAGS = $(MDOC_COMMON_FLAGS) \
-       /r:monodoc.dll
+
+LIB_REFS = monodoc System System.Xml System.Core Mono.Cecil ICSharpCode.SharpZipLib System.Xml.Linq System.Web
+       
+LOCAL_MCS_FLAGS = $(MDOC_COMMON_FLAGS)
 PROGRAM = mdoc.exe
 PROGRAM_DEPS = $(topdir)/class/lib/$(PROFILE)/monodoc.dll
 
@@ -98,51 +92,51 @@ cleanup:
        -rm -f monodocer1.exe*
 
 Test/DocTest-addNonGeneric.dll:
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-addNonGeneric.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-addNonGeneric.cs
 
 Test/DocTest-addNonGeneric-v2.dll:
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-addNonGeneric.cs /define:V2
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-addNonGeneric.cs /define:V2
 
 Test/DocTest-DropNS-classic-secondary.dll:
        @echo $(value @)
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic-secondary.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic-secondary.cs
 
 Test/DocTest-DropNS-classic.dll:
        @echo $(value @)
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs
 
 Test/DocTest-DropNS-unified.dll:
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs
 
 Test/DocTest-DropNS-unified-multitest.dll:
        rm -f $@
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs /define:MULTITEST
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs /define:MULTITEST
 
 Test/DocTest-DropNS-classic-multitest.dll:
        rm -f $@
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs /define:MULTITEST
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs /define:MULTITEST
 
 Test/DocTest-DropNS-unified-deletetest.dll:
        rm -f Test/DocTest-DropNS-unified-deletetest.dll
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs /define:DELETETEST
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-unified.cs /define:DELETETEST
 
 Test/DocTest-DropNS-unified-deletetest-V2.dll:
        rm -f Test/DocTest-DropNS-unified-deletetest.dll
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:Test/DocTest-DropNS-unified-deletetest.dll Test/DocTest-DropNS-unified.cs /define:DELETETEST,V2
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:Test/DocTest-DropNS-unified-deletetest.dll Test/DocTest-DropNS-unified.cs /define:DELETETEST,V2
 
 Test/DocTest-DropNS-classic-deletetest.dll:
        rm -f Test/DocTest-DropNS-classic-deletetest.dll
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs /define:DELETETEST
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-DropNS-classic.cs /define:DELETETEST
 
 Test/DocTest-DropNS-classic-deletetest-V2.dll:
        rm -f Test/DocTest-DropNS-classic-deletetest.dll
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:Test/DocTest-DropNS-classic-deletetest.dll Test/DocTest-DropNS-classic.cs /define:DELETETEST,V2
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:Test/DocTest-DropNS-classic-deletetest.dll Test/DocTest-DropNS-classic.cs /define:DELETETEST,V2
 
 Test/DocTest.dll: 
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest.cs -r:$(topdir)/class/lib/$(PROFILE)/System.Core.dll -r:$(topdir)/class/lib/$(PROFILE)/Microsoft.CSharp.dll
 
 Test/DocTest-InternalInterface.dll: 
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-InternalInterface.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-InternalInterface.cs
 
 Test/DocTest.dll-v1: 
        -rm -f Test/DocTest.cs
@@ -158,7 +152,7 @@ Test/DocTest.dll-v2:
        $(MAKE) TEST_CSCFLAGS=$(TEST_CSCFLAGS) Test/DocTest.dll
 
 Test/DocTest-enumerations.dll: 
-       $(CSCOMPILE) $(TEST_CSCFLAGS) -debug -unsafe -target:library -out:$@ Test/DocTest-enumerations.cs
+       $(CSCOMPILE) $(TEST_CSCFLAGS) -unsafe -target:library -out:$@ Test/DocTest-enumerations.cs
 
 check-monodocer-addNonGeneric: $(PROGRAM)
        -rm -Rf Test/en.actual
index 44620aacd1fef6eedb2d430e917e391cbb334099..05faf5e8c685e1ec0ce4d295e848619f974d28c8 100644 (file)
@@ -10,7 +10,8 @@ RESOURCE_FILES = $(OTHER_RES)
 
 LOCAL_MCS_FLAGS= $(OTHER_RES:%=-resource:%)
 
-LOCAL_MCS_FLAGS += -d:STATIC,NO_SYMBOL_WRITER,NO_AUTHENTICODE -r:System.Xml.dll -r:System.dll
+LOCAL_MCS_FLAGS += -d:STATIC,NO_SYMBOL_WRITER,NO_AUTHENTICODE
+LIB_REFS = System.Xml System System.Core
 
 EXTRA_DISTFILES = $(RESOURCE_FILES)
 
index 46c63cd9dfeff02e3431f06c12e0317b3b25f3be..6395e90ff41b3499337d075e126a72376dd6f35e 100755 (executable)
@@ -7,6 +7,11 @@
 //   Miguel de Icaza
 //
 // (C) Novell, Inc 2004
+// (C) 2016 Xamarin Inc
+//
+// Missing features:
+// * Implement --cross, --local-targets, --list-targets, --no-auto-fetch
+// * concatenate target with package to form native binary
 //
 using System;
 using System.Diagnostics;
@@ -17,8 +22,8 @@ using System.IO.Compression;
 using System.Runtime.InteropServices;
 using System.Text;
 using IKVM.Reflection;
-
-
+using System.Linq;
+using System.Diagnostics;
 using System.Threading.Tasks;
 
 class MakeBundle {
@@ -41,6 +46,9 @@ class MakeBundle {
        static bool skip_scan;
        static string ctor_func;
        static bool quiet;
+       static bool custom_mode = true;
+       static string embedded_options = null;
+       static string runtime = null;
        
        static int Main (string [] args)
        {
@@ -56,6 +64,15 @@ class MakeBundle {
                                Help ();
                                return 1;
 
+                       case "--simple":
+                               custom_mode = false;
+                               autodeps = true;
+                               break;
+                               
+                       case "--custom":
+                               custom_mode = true;
+                               break;
+                               
                        case "-c":
                                compile_only = true;
                                break;
@@ -68,6 +85,20 @@ class MakeBundle {
                                output = args [++i];
                                break;
 
+                       case "--options":
+                               if (i+1 == top){
+                                       Help (); 
+                                       return 1;
+                               }
+                               embedded_options = args [++i];
+                               break;
+                       case "--runtime":
+                               if (i+1 == top){
+                                       Help (); 
+                                       return 1;
+                               }
+                               runtime = args [++i];
+                               break;
                        case "-oo":
                                if (i+1 == top){
                                        Help (); 
@@ -95,12 +126,9 @@ class MakeBundle {
                        case "--keeptemp":
                                keeptemp = true;
                                break;
+                               
                        case "--static":
                                static_link = true;
-                               if (!quiet) {
-                                       Console.WriteLine ("Note that statically linking the LGPL Mono runtime has more licensing restrictions than dynamically linking.");
-                                       Console.WriteLine ("See http://www.mono-project.com/Licensing for details on licensing.");
-                               }
                                break;
                        case "--config":
                                if (i+1 == top) {
@@ -201,9 +229,11 @@ class MakeBundle {
                foreach (string file in assemblies)
                        if (!QueueAssembly (files, file))
                                return 1;
-                       
-               GenerateBundles (files);
-               //GenerateJitWrapper ();
+
+               if (custom_mode)
+                       GenerateBundles (files);
+               else
+                       GeneratePackage (files);
                
                return 0;
        }
@@ -268,6 +298,138 @@ class MakeBundle {
 
                ts.WriteLine ();
        }
+
+       class PackageMaker {
+               Dictionary<string, Tuple<long,int>> locations = new Dictionary<string, Tuple<long,int>> ();
+               const int align = 4096;
+               Stream package;
+               
+               public PackageMaker (string output)
+               {
+                       package = File.Create (output, 128*1024);
+                       if (IsUnix){
+                               File.SetAttributes (output, unchecked ((FileAttributes) 0x80000000));
+                       }
+               }
+
+               public int AddFile (string fname)
+               {
+                       using (Stream fileStream = File.OpenRead (fname)){
+                               var ret = fileStream.Length;
+                               
+                               Console.WriteLine ("At {0:x} with input {1}", package.Position, fileStream.Length);
+                               fileStream.CopyTo (package);
+                               package.Position = package.Position + (align - (package.Position % align));
+
+                               return (int) ret;
+                       }
+               }
+               
+               public void Add (string entry, string fname)
+               {
+                       var p = package.Position;
+                       var size = AddFile (fname);
+                       
+                       locations [entry] = Tuple.Create(p, size);
+               }
+
+               public void AddString (string entry, string text)
+               {
+                       var bytes = Encoding.UTF8.GetBytes (text);
+                       locations [entry] = Tuple.Create (package.Position, bytes.Length);
+                       package.Write (bytes, 0, bytes.Length);
+                       package.Position = package.Position + (align - (package.Position % align));
+               }
+
+               public void Dump ()
+               {
+                       foreach (var floc in locations.Keys){
+                               Console.WriteLine ($"{floc} at {locations[floc]:x}");
+                       }
+               }
+
+               public void WriteIndex ()
+               {
+                       var indexStart = package.Position;
+                       var binary = new BinaryWriter (package);
+
+                       binary.Write (locations.Count);
+                       foreach (var entry in from entry in locations orderby entry.Value.Item1 ascending select entry){
+                               var bytes = Encoding.UTF8.GetBytes (entry.Key);
+                               binary.Write (bytes.Length+1);
+                               binary.Write (bytes);
+                               binary.Write ((byte) 0);
+                               binary.Write (entry.Value.Item1);
+                               binary.Write (entry.Value.Item2);
+                       }
+                       binary.Write (indexStart);
+                       binary.Write (Encoding.UTF8.GetBytes ("xmonkeysloveplay"));
+                       binary.Flush ();
+               }
+               
+               public void Close ()
+               {
+                       WriteIndex ();
+                       package.Close ();
+                       package = null;
+               }
+       }
+
+       static bool MaybeAddFile (PackageMaker maker, string code, string file)
+       {
+               if (file == null)
+                       return true;
+               
+               if (!File.Exists (file)){
+                       Console.Error.WriteLine ("The file {0} does not exist", file);
+                       return false;
+               }
+               maker.Add (code, file);
+               return true;
+       }
+       
+       static bool GeneratePackage (List<string> files)
+       {
+               if (runtime == null){
+                       if (IsUnix)
+                               runtime = Process.GetCurrentProcess().MainModule.FileName;
+                       else {
+                               Console.Error.WriteLine ("You must specify at least one runtime with --runtime or --cross");
+                               Environment.Exit (1);
+                       }
+               }
+               if (!File.Exists (runtime)){
+                       Console.Error.WriteLine ($"The specified runtime at {runtime} does not exist");
+                       Environment.Exit (1);
+               }
+               
+               if (ctor_func != null){
+                       Console.Error.WriteLine ("--static-ctor not supported with package bundling, you must use native compilation for this");
+                       return false;
+               }
+               
+               var maker = new PackageMaker (output);
+               maker.AddFile (runtime);
+               
+               foreach (var url in files){
+                       string fname = LocateFile (new Uri (url).LocalPath);
+                       string aname = Path.GetFileName (fname);
+
+                       maker.Add ("assembly:" + aname, fname);
+                       if (File.Exists (fname + ".config"))
+                               maker.Add ("config:" + aname, fname + ".config");
+               }
+               if (!MaybeAddFile (maker, "systemconfig:", config_file) || !MaybeAddFile (maker, "machineconfig:", machine_config_file))
+                       return false;
+
+               if (config_dir != null)
+                       maker.Add ("config_dir:", config_dir);
+               if (embedded_options != null)
+                       maker.AddString ("options:", embedded_options);
+               maker.Dump ();
+               maker.Close ();
+               return true;
+       }
        
        static void GenerateBundles (List<string> files)
        {
@@ -760,25 +922,35 @@ void          mono_register_config_for_assembly (const char* assembly_name, cons
        {
                Console.WriteLine ("Usage is: mkbundle [options] assembly1 [assembly2...]\n\n" +
                                   "Options:\n" +
-                                  "    -c                  Produce stub only, do not compile\n" +
+                                  "    --config F          Bundle system config file `F'\n" +
+                                  "    --config-dir D      Set MONO_CFG_DIR to `D'\n" +
+                                  "    --deps              Turns on automatic dependency embedding (default on simple)\n" +
+                                  "    -L path             Adds `path' to the search path for assemblies\n" +
+                                  "    --machine-config F  Use the given file as the machine.config for the application.\n" +
                                   "    -o out              Specifies output filename\n" +
+                                  "    --nodeps            Turns off automatic dependency embedding (default on custom)\n" +
+                                  "    --skip-scan         Skip scanning assemblies that could not be loaded (but still embed them).\n" +
+                                  "\n" + 
+                                  "--simple   Simple mode does not require a C toolchain and can cross compile\n" + 
+                                  "    --cross TARGET      Generates a binary for the given TARGET\n"+
+                                  "    --local-targets     Lists locally available targets\n" +
+                                  "    --list-targets [SERVER] Lists available targets on the remote server\n" +
+                                  "    --no-auto-fetch     Prevents the tool from auto-fetching a TARGET\n" +
+                                  "    --options OPTIONS   Embed the specified Mono command line options on target\n" +
+                                  "    --runtime RUNTIME   Manually specifies the Mono runtime to use\n" + 
+                                  "\n" +
+                                  "--custom   Builds a custom launcher, options for --custom\n" +
+                                  "    -c                  Produce stub only, do not compile\n" +
                                   "    -oo obj             Specifies output filename for helper object file\n" +
-                                  "    -L path             Adds `path' to the search path for assemblies\n" +
-                                  "    --nodeps            Turns off automatic dependency embedding (default)\n" +
-                                  "    --deps              Turns on automatic dependency embedding\n" +
                                   "    --dos2unix[=true|false]\n" +
                                   "                        When no value provided, or when `true` specified\n" +
                                   "                        `dos2unix` will be invoked to convert paths on Windows.\n" +
                                   "                        When `--dos2unix=false` used, dos2unix is NEVER used.\n" +
                                   "    --keeptemp          Keeps the temporary files\n" +
-                                  "    --config F          Bundle system config file `F'\n" +
-                                  "    --config-dir D      Set MONO_CFG_DIR to `D'\n" +
-                                  "    --machine-config F  Use the given file as the machine.config for the application.\n" +
                                   "    --static            Statically link to mono libs\n" +
                                   "    --nomain            Don't include a main() function, for libraries\n" +
-                                  "    --custom-main C         Link the specified compilation unit (.c or .obj) with entry point/init code\n" +
+                                  "    --custom-main C     Link the specified compilation unit (.c or .obj) with entry point/init code\n" +
                                   "    -z                  Compress the assemblies before embedding.\n" +
-                                  "    --skip-scan         Skip scanning assemblies that could not be loaded (but still embed them).\n" +
                                   "    --static-ctor ctor  Add a constructor call to the supplied function.\n" +
                                   "                        You need zlib development headers and libraries.\n");
        }
index 90c9afcb026b42f8208b7e4bc4ea6ce7bf61fff9..35133d61dbe817bc079816a88ef6337606ef4385 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mod
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = /r:monodoc.dll
+LIB_REFS = monodoc
+LOCAL_MCS_FLAGS =
 
 PROGRAM = mod.exe
 
diff --git a/mcs/tools/mono-api-html/ApiChange.cs b/mcs/tools/mono-api-html/ApiChange.cs
new file mode 100644 (file)
index 0000000..1d902ca
--- /dev/null
@@ -0,0 +1,81 @@
+using System;
+using System.Collections.Generic;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff
+{
+       public class ApiChange
+       {
+               public string Header;
+               public StringBuilder Member = new StringBuilder ();
+               public bool Breaking;
+               public bool AnyChange;
+               public bool HasIgnoredChanges;
+
+               public ApiChange Append (string text)
+               {
+                       Member.Append (text);
+                       return this;
+               }
+
+               public ApiChange AppendAdded (string text, bool breaking = false)
+               {
+                       Member.Append ("<span class='added ").Append (breaking ? "added-breaking-inline" : string.Empty).Append ("'>");
+                       Member.Append (text);
+                       Member.Append ("</span>");
+                       Breaking |= breaking;
+                       AnyChange = true;
+                       return this;
+               }
+
+               public ApiChange AppendRemoved (string text, bool breaking = true)
+               {
+                       Member.Append ("<span class='removed removed-inline ").Append (breaking ? "removed-breaking-inline" : string.Empty).Append ("'>");
+                       Member.Append (text);
+                       Member.Append ("</span>");
+                       Breaking |= breaking;
+                       AnyChange = true;
+                       return this;
+               }
+
+               public ApiChange AppendModified (string old, string @new, bool breaking = true)
+               {
+                       if (old.Length > 0)
+                               AppendRemoved (old, breaking);
+                       if (old.Length > 0 && @new.Length > 0)
+                               Append (" ");
+                       if (@new.Length > 0)
+                               AppendAdded (@new);
+                       Breaking |= breaking;
+                       AnyChange = true;
+                       return this;
+               }
+       }
+
+       public class ApiChanges : Dictionary<string, List<ApiChange>> {
+               public void Add (XElement source, XElement target, ApiChange change)
+               {
+                       if (!change.AnyChange) {
+                               // This is most likely because the rendering doesn't take into account something that's different (solution: fix rendering).
+                               if (!change.HasIgnoredChanges) {
+                                       var isField = source.Name.LocalName == "field";
+                                       if (isField) {
+                                               Console.WriteLine ("Comparison resulting in no changes (src: {2} dst: {3}) :\n{0}\n{1}\n\n", source.ToString (), target.ToString (), source.GetFieldAttributes (), target.GetFieldAttributes ());
+                                       } else {
+                                               Console.WriteLine ("Comparison resulting in no changes (src: {2} dst: {3}) :\n{0}\n{1}\n\n", source.ToString (), target.ToString (), source.GetMethodAttributes (), target.GetMethodAttributes ());
+                                       }
+                               }
+                               return;
+                       }
+
+                       List<ApiChange> list;
+                       if (!TryGetValue (change.Header, out list)) {
+                               list = new List<ApiChange> ();
+                               base.Add (change.Header, list);
+                       }
+                       list.Add (change);
+               }
+       }
+}
+
diff --git a/mcs/tools/mono-api-html/ApiDiff.cs b/mcs/tools/mono-api-html/ApiDiff.cs
new file mode 100644 (file)
index 0000000..8fe2784
--- /dev/null
@@ -0,0 +1,277 @@
+//
+// The main differences with mono-api-diff are:
+// * this tool directly produce HTML similar to gdiff.sh used for Xamarin.iOS
+// * this tool reports changes in an "evolutionary" way, not in a breaking way,
+//   i.e. it does not assume the source assembly is right (but simply older)
+// * the diff .xml output was not easy to convert back into the HTML format
+//   that gdiff.sh produced
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.IO;
+using System.Collections.Generic;
+using System.Text.RegularExpressions;
+
+using Mono.Options;
+
+namespace Xamarin.ApiDiff {
+
+       public static class State {
+               static TextWriter output;
+
+               public static TextWriter Output { 
+                       get {
+                               if (output == null)
+                                       output = Console.Out;
+                               return output;
+                       }
+                       set { output = value; } 
+               }
+
+               public static string Assembly { get; set; }
+               public static string Namespace { get; set; }
+               public static string Type { get; set; }
+               public static string BaseType { get; set; }
+
+               public static int Indent { get; set; }
+
+               static List<Regex> ignoreAdded = new List<Regex> ();
+               public static List<Regex> IgnoreAdded {
+                       get { return ignoreAdded; }
+               }
+
+               static List<Regex> ignoreNew = new List<Regex> ();
+               public static List<Regex> IgnoreNew {
+                       get { return ignoreNew; }
+               }
+
+               static List<Regex> ignoreRemoved = new List<Regex> ();
+               public static List<Regex> IgnoreRemoved {
+                       get { return ignoreRemoved; }
+               }
+
+               public  static  bool    IgnoreParameterNameChanges  { get; set; }
+               public  static  bool    IgnoreVirtualChanges        { get; set; }
+               public  static  bool    IgnoreAddedPropertySetters  { get; set; }
+
+               public static bool Lax;
+               public static bool Colorize = true;
+       }
+
+       class Program {
+
+               public static int Main (string[] args)
+               {
+                       var showHelp = false;
+                       string diff = null;
+                       List<string> extra = null;
+
+                       var options = new OptionSet {
+                               { "h|help", "Show this help", v => showHelp = true },
+                               { "d|diff=", "HTML diff file out output (omit for stdout)", v => diff = v },
+                               { "i|ignore=", "Ignore new, added, and removed members whose description matches a given C# regular expression (see below).",
+                                       v => {
+                                               var r = new Regex (v);
+                                               State.IgnoreAdded.Add (r);
+                                               State.IgnoreRemoved.Add (r);
+                                               State.IgnoreNew.Add (r);
+                                       }
+                               },
+                               { "a|ignore-added=", "Ignore added members whose description matches a given C# regular expression (see below).",
+                                       v => State.IgnoreAdded.Add (new Regex (v))
+                               },
+                               { "r|ignore-removed=", "Ignore removed members whose description matches a given C# regular expression (see below).",
+                                       v => State.IgnoreRemoved.Add (new Regex (v))
+                               },
+                               { "n|ignore-new=", "Ignore new namespaces and types whose description matches a given C# regular expression (see below).",
+                                       v => State.IgnoreNew.Add (new Regex (v))
+                               },
+                               { "ignore-changes-parameter-names", "Ignore changes to parameter names for identically prototyped methods.",
+                                       v => State.IgnoreParameterNameChanges   = v != null
+                               },
+                               { "ignore-changes-property-setters", "Ignore adding setters to properties.",
+                                       v => State.IgnoreAddedPropertySetters = v != null
+                               },
+                               { "ignore-changes-virtual", "Ignore changing non-`virtual` to `virtual` or adding `override`.",
+                                       v => State.IgnoreVirtualChanges = v != null
+                               },
+                               { "c|colorize:", "Colorize HTML output", v => State.Colorize = string.IsNullOrEmpty (v) ? true : bool.Parse (v) },
+                               { "x|lax", "Ignore duplicate XML entries", v => State.Lax = true }
+                       };
+
+                       try {
+                               extra = options.Parse (args);
+                       } catch (OptionException e) {
+                               Console.WriteLine ("Option error: {0}", e.Message);
+                               showHelp = true;
+                       }
+
+                       if (showHelp || extra == null || extra.Count < 2 || extra.Count > 3) {
+                               Console.WriteLine (@"Usage: mono-api-html [options] <reference.xml> <assembly.xml> [diff.html]");
+                               Console.WriteLine ();
+                               Console.WriteLine ("Available options:");
+                               options.WriteOptionDescriptions (Console.Out);
+                               Console.WriteLine ();
+                               Console.WriteLine ("Ignoring Members:");
+                               Console.WriteLine ();
+                               Console.WriteLine ("  Members that were added can be filtered out of the diff by using the");
+                               Console.WriteLine ("  -i, --ignore-added option. The option takes a C# regular expression");
+                               Console.WriteLine ("  to match against member descriptions. For example, to ignore the");
+                               Console.WriteLine ("  introduction of the interfaces 'INSCopying' and 'INSCoding' on types");
+                               Console.WriteLine ("  pass the following to mono-api-html:");
+                               Console.WriteLine ();
+                               Console.WriteLine ("    mono-api-html ... -i 'INSCopying$' -i 'INSCoding$'");
+                               Console.WriteLine ();
+                               Console.WriteLine ("  The regular expressions will match any member description ending with");
+                               Console.WriteLine ("  'INSCopying' or 'INSCoding'.");
+                               Console.WriteLine ();
+                               return 1;
+                       }
+
+                       var input = extra [0];
+                       var output = extra [1];
+                       if (extra.Count == 3 && diff == null)
+                               diff = extra [2];
+
+                       try {
+                               var ac = new AssemblyComparer (input, output);
+                               if (diff != null) {
+                                       string diffHtml = String.Empty;
+                                       using (var writer = new StringWriter ()) {
+                                               State.Output = writer;
+                                               ac.Compare ();
+                                               diffHtml = State.Output.ToString ();
+                                       }
+                                       if (diffHtml.Length > 0) {
+                                               using (var file = new StreamWriter (diff)) {
+                                                       file.WriteLine ("<div>");
+                                                       if (State.Colorize) {
+                                                               file.WriteLine ("<style scoped>");
+                                                               file.WriteLine ("\t.obsolete { color: gray; }");
+                                                               file.WriteLine ("\t.added { color: green; }");
+                                                               file.WriteLine ("\t.removed-inline { text-decoration: line-through; }");
+                                                               file.WriteLine ("\t.removed-breaking-inline { color: red;}");
+                                                               file.WriteLine ("\t.added-breaking-inline { text-decoration: underline; }");
+                                                               file.WriteLine ("\t.nonbreaking { color: black; }");
+                                                               file.WriteLine ("\t.breaking { color: red; }");
+                                                               file.WriteLine ("</style>");
+                                                       }
+                                                       file.WriteLine (
+@"<script type=""text/javascript"">
+       // Only some elements have 'data-is-[non-]breaking' attributes. Here we
+       // iterate over all descendents elements, and set 'data-is-[non-]breaking'
+       // depending on whether there are any descendents with that attribute.
+       function propagateDataAttribute (element)
+       {
+               if (element.hasAttribute ('data-is-propagated'))
+                       return;
+
+               var i;
+               var any_breaking = element.hasAttribute ('data-is-breaking');
+               var any_non_breaking = element.hasAttribute ('data-is-non-breaking');
+               for (i = 0; i < element.children.length; i++) {
+                       var el = element.children [i];
+                       propagateDataAttribute (el);
+                       any_breaking |= el.hasAttribute ('data-is-breaking');
+                       any_non_breaking |= el.hasAttribute ('data-is-non-breaking');
+               }
+               
+               if (any_breaking)
+                       element.setAttribute ('data-is-breaking', null);
+               else if (any_non_breaking)
+                       element.setAttribute ('data-is-non-breaking', null);
+               element.setAttribute ('data-is-propagated', null);
+       }
+
+       function hideNonBreakingChanges ()
+       {
+               var topNodes = document.querySelectorAll ('[data-is-topmost]');
+               var n;
+               var i;
+               for (n = 0; n < topNodes.length; n++) {
+                       propagateDataAttribute (topNodes [n]);
+                       var elements = topNodes [n].querySelectorAll ('[data-is-non-breaking]');
+                       for (i = 0; i < elements.length; i++) {
+                               var el = elements [i];
+                               if (!el.hasAttribute ('data-original-display'))
+                                       el.setAttribute ('data-original-display', el.style.display);
+                               el.style.display = 'none';
+                       }
+               }
+               
+               var links = document.getElementsByClassName ('hide-nonbreaking');
+               for (i = 0; i < links.length; i++)
+                       links [i].style.display = 'none';
+               links = document.getElementsByClassName ('restore-nonbreaking');
+               for (i = 0; i < links.length; i++)
+                       links [i].style.display = '';
+       }
+
+       function showNonBreakingChanges ()
+       {
+               var elements = document.querySelectorAll ('[data-original-display]');
+               var i;
+               for (i = 0; i < elements.length; i++) {
+                       var el = elements [i];
+                       el.style.display = el.getAttribute ('data-original-display');
+               }
+
+               var links = document.getElementsByClassName ('hide-nonbreaking');
+               for (i = 0; i < links.length; i++)
+                       links [i].style.display = '';
+               links = document.getElementsByClassName ('restore-nonbreaking');
+               for (i = 0; i < links.length; i++)
+                       links [i].style.display = 'none';
+       }
+</script>");
+                                                       if (ac.SourceAssembly == ac.TargetAssembly) {
+                                                               file.WriteLine ("<h1>{0}.dll</h1>", ac.SourceAssembly);
+                                                       } else {
+                                                               file.WriteLine ("<h1>{0}.dll vs {1}.dll</h1>", ac.SourceAssembly, ac.TargetAssembly);
+                                                       }
+                                                       file.WriteLine ("<a href='javascript: hideNonBreakingChanges (); ' class='hide-nonbreaking'>Hide non-breaking changes</a>");
+                                                       file.WriteLine ("<a href='javascript: showNonBreakingChanges (); ' class='restore-nonbreaking' style='display: none;'>Show non-breaking changes</a>");
+                                                       file.WriteLine ("<br/>");
+                                                       file.WriteLine ("<div data-is-topmost>");
+                                                       file.Write (diffHtml);
+                                                       file.WriteLine ("</div> <!-- end topmost div -->");
+                                                       file.WriteLine ("</div>");
+                                               }
+                                       }
+                               } else {
+                                       State.Output = Console.Out;
+                                       ac.Compare ();
+                               }
+                       }
+                       catch (Exception e) {
+                               Console.WriteLine (e);
+                               return 1;
+                       }
+                       return 0;
+               }
+       }
+}
diff --git a/mcs/tools/mono-api-html/AssemblyComparer.cs b/mcs/tools/mono-api-html/AssemblyComparer.cs
new file mode 100644 (file)
index 0000000..adbd862
--- /dev/null
@@ -0,0 +1,79 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class AssemblyComparer : Comparer {
+
+               XDocument source;
+               XDocument target;
+               NamespaceComparer comparer;
+
+               public AssemblyComparer (string sourceFile, string targetFile)
+               {
+                       source = XDocument.Load (sourceFile);
+                       target = XDocument.Load (targetFile);
+                       comparer =  new NamespaceComparer ();
+               }
+
+               public string SourceAssembly { get; private set; }
+               public string TargetAssembly { get; private set; }
+
+               public void Compare ()
+               {
+                       Compare (source.Element ("assemblies").Elements ("assembly"), 
+                                target.Element ("assemblies").Elements ("assembly"));
+               }
+
+               public override void SetContext (XElement current)
+               {
+                       State.Assembly = current.GetAttribute ("name");
+               }
+
+               public override void Added (XElement target, bool wasParentAdded)
+               {
+                       // one assembly per xml file
+               }
+
+               public override void Modified (XElement source, XElement target, ApiChanges diff)
+               {
+                       SourceAssembly = source.GetAttribute ("name");
+                       TargetAssembly = target.GetAttribute ("name");
+                       // TODO: version
+                       // ? custom attributes ?
+                       comparer.Compare (source, target);
+               }
+
+               public override void Removed (XElement source)
+               {
+                       // one assembly per xml file
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/ClassComparer.cs b/mcs/tools/mono-api-html/ClassComparer.cs
new file mode 100644 (file)
index 0000000..a3399fb
--- /dev/null
@@ -0,0 +1,261 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class ClassComparer : Comparer {
+
+               InterfaceComparer icomparer;
+               ConstructorComparer ccomparer;
+               FieldComparer fcomparer;
+               PropertyComparer pcomparer;
+               EventComparer ecomparer;
+               MethodComparer mcomparer;
+               ClassComparer kcomparer;
+
+               public ClassComparer ()
+               {
+                       icomparer = new InterfaceComparer ();
+                       ccomparer = new ConstructorComparer ();
+                       fcomparer = new FieldComparer ();
+                       pcomparer = new PropertyComparer ();
+                       ecomparer = new EventComparer ();
+                       mcomparer = new MethodComparer ();
+               }
+
+               public override void SetContext (XElement current)
+               {
+                       State.Type = current.GetAttribute ("name");
+                       State.BaseType = current.GetAttribute ("base");
+               }
+
+               public void Compare (XElement source, XElement target)
+               {
+                       var s = source.Element ("classes");
+                       var t = target.Element ("classes");
+                       if (XNode.DeepEquals (s, t))
+                               return;
+                       Compare (s.Elements ("class"), t.Elements ("class"));
+               }
+
+               public override void Added (XElement target, bool wasParentAdded)
+               {
+                       string name = target.Attribute ("name").Value;
+                       if (State.IgnoreNew.Any (re => re.IsMatch (name)))
+                               return;
+                       Output.WriteLine ("<div> <!-- start type {0} -->", name);
+                       Output.WriteLine ("<h3>New Type {0}.{1}</h3>", State.Namespace, name);
+                       Output.WriteLine ("<pre class='added' data-is-non-breaking>");
+                       State.Indent = 0;
+                       AddedInner (target);
+                       Output.WriteLine ("</pre>");
+                       Output.WriteLine ("</div> <!-- end type {0} -->", name);
+               }
+
+               public void AddedInner (XElement target)
+               {
+                       SetContext (target);
+                       if (target.IsTrue ("serializable"))
+                               Indent ().WriteLine ("[Serializable]");
+
+                       var type = target.Attribute ("type").Value;
+
+                       if (type == "enum") {
+                               // check if [Flags] is present
+                               var cattrs = target.Element ("attributes");
+                               if (cattrs != null) {
+                                       foreach (var ca in cattrs.Elements ("attribute")) {
+                                               if (ca.GetAttribute ("name") == "System.FlagsAttribute") {
+                                                       Indent ().WriteLine ("[Flags]");
+                                                       break;
+                                               }
+                                       }
+                               }
+                       }
+
+                       Indent ().Write ("public");
+
+                       if (type != "enum") {
+                               bool seal = target.IsTrue ("sealed");
+                               bool abst = target.IsTrue ("abstract");
+                               if (seal && abst)
+                                       Output.Write (" static");
+                               else if (seal && type != "struct")
+                                       Output.Write (" sealed");
+                               else if (abst && type != "interface")
+                                       Output.Write (" abstract");
+                       }
+
+                       Output.Write (' ');
+                       Output.Write (type);
+                       Output.Write (' ');
+                       Output.Write (target.GetAttribute ("name"));
+
+                       var baseclass = target.GetAttribute ("base");
+                       if ((type != "enum") && (type != "struct")) {
+                               if (baseclass != null) {
+                                       if (baseclass == "System.Object") {
+                                               // while true we do not need to be reminded every time...
+                                               baseclass = null;
+                                       } else {
+                                               Output.Write (" : ");
+                                               Output.Write (baseclass);
+                                       }
+                               }
+                       }
+
+                       // interfaces on enums are "standard" not user provided - so we do not want to show them
+                       if (type != "enum") {
+                               var i = target.Element ("interfaces");
+                               if (i != null) {
+                                       var interfaces = new List<string> ();
+                                       foreach (var iface in i.Elements ("interface"))
+                                               interfaces.Add (icomparer.GetDescription (iface));
+                                       Output.Write ((baseclass == null) ? " : " : ", ");
+                                       Output.Write (String.Join (", ", interfaces));
+                               }
+                       }
+
+                       Output.WriteLine (" {");
+
+                       var t = target.Element ("constructors");
+                       if (t != null) {
+                               Indent ().WriteLine ("\t// constructors");
+                               foreach (var ctor in t.Elements ("constructor"))
+                                       ccomparer.Added (ctor, true);
+                       }
+
+                       t = target.Element ("fields");
+                       if (t != null) {
+                               if (type != "enum")
+                                       Indent ().WriteLine ("\t// fields");
+                               else
+                                       SetContext (target);
+                               foreach (var field in t.Elements ("field"))
+                                       fcomparer.Added (field, true);
+                       }
+
+                       t = target.Element ("properties");
+                       if (t != null) {
+                               Indent ().WriteLine ("\t// properties");
+                               foreach (var property in t.Elements ("property"))
+                                       pcomparer.Added (property, true);
+                       }
+
+                       t = target.Element ("events");
+                       if (t != null) {
+                               Indent ().WriteLine ("\t// events");
+                               foreach (var evnt in t.Elements ("event"))
+                                       ecomparer.Added (evnt, true);
+                       }
+
+                       t = target.Element ("methods");
+                       if (t != null) {
+                               Indent ().WriteLine ("\t// methods");
+                               foreach (var method in t.Elements ("method"))
+                                       mcomparer.Added (method, true);
+                       }
+
+                       t = target.Element ("classes");
+                       if (t != null) {
+                               Output.WriteLine ();
+                               Indent ().WriteLine ("\t// inner types");
+                               kcomparer = new NestedClassComparer ();
+                               State.Indent++;
+                               foreach (var inner in t.Elements ("class"))
+                                       kcomparer.AddedInner (inner);
+                               State.Indent--;
+                       }
+                       Indent ().WriteLine ("}");
+               }
+
+               public override void Modified (XElement source, XElement target, ApiChanges diff)
+               {
+                       // hack - there could be changes that we're not monitoring (e.g. attributes properties)
+                       var output = Output;
+                       State.Output = new StringWriter ();
+
+                       var sb = source.GetAttribute ("base");
+                       var tb = target.GetAttribute ("base");
+                       if (sb != tb) {
+                               Output.Write ("Modified base type: ");
+                               Output.WriteLine (new ApiChange ().AppendModified (sb, tb, true).Member.ToString ());
+                       }
+
+                       ccomparer.Compare (source, target);
+                       icomparer.Compare (source, target);
+                       fcomparer.Compare (source, target);
+                       pcomparer.Compare (source, target);
+                       ecomparer.Compare (source, target);
+                       mcomparer.Compare (source, target);
+
+                       var si = source.Element ("classes");
+                       if (si != null) {
+                               var ti = target.Element ("classes");
+                               kcomparer = new NestedClassComparer ();
+                               kcomparer.Compare (si.Elements ("class"), ti == null ? null : ti.Elements ("class"));
+                       }
+
+                       var s = (Output as StringWriter).ToString ();
+                       State.Output = output;
+                       if (s.Length > 0) {
+                               var tn = GetTypeName (target);
+                               Output.WriteLine ("<!-- start type {0} --> <div>", tn);
+                               Output.WriteLine ("<h3>Type Changed: {0}.{1}</h3>", State.Namespace, GetTypeName (target));
+                               Output.WriteLine (s);
+                               Output.WriteLine ("</div> <!-- end type {0} -->", tn);
+                       }
+               }
+
+               public override void Removed (XElement source)
+               {
+                       Output.Write ("<h3>Removed Type <span class='breaking' data-is-breaking>{0}.{1}</span></h3>", State.Namespace, GetTypeName (source));
+               }
+
+               public virtual string GetTypeName (XElement type)
+               {
+                       return type.GetAttribute ("name");
+               }
+       }
+
+       public class NestedClassComparer : ClassComparer {
+
+               public override void SetContext (XElement current)
+               {
+               }
+
+               public override string GetTypeName (XElement type)
+               {
+                       return State.Type + "." + base.GetTypeName (type);
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/Comparer.cs b/mcs/tools/mono-api-html/Comparer.cs
new file mode 100644 (file)
index 0000000..4210b9b
--- /dev/null
@@ -0,0 +1,98 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public abstract class Comparer {
+
+               protected List<XElement> removed = new List<XElement> ();
+               protected ApiChanges modified = new ApiChanges ();
+
+               public TextWriter Output {
+                       get { return State.Output; }
+               }
+
+               protected TextWriter Indent ()
+               {
+                       for (int i = 0; i < State.Indent; i++)
+                               State.Output.Write ("\t");
+                       return State.Output;
+               }
+
+               public abstract void Added (XElement target, bool wasParentAdded);
+               public abstract void Modified (XElement source, XElement target, ApiChanges changes);
+               public abstract void Removed (XElement source);
+
+               public virtual bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       return XNode.DeepEquals (source, target);
+               }
+
+               public abstract void SetContext (XElement current);
+
+               public virtual void Compare (IEnumerable<XElement> source, IEnumerable<XElement> target)
+               {
+                       removed.Clear ();
+                       modified.Clear ();
+
+                       foreach (var s in source) {
+                               SetContext (s);
+                               string sn = s.GetAttribute ("name");
+                               var t = target == null ? null : target.SingleOrDefault (x => x.GetAttribute ("name") == sn);
+                               if (t == null) {
+                                       // not in target, it was removed
+                                       removed.Add (s);
+                               } else {
+                                       t.Remove ();
+                                       // possibly modified
+                                       if (Equals (s, t, modified))
+                                               continue;
+
+                                       // still in target so will be part of Added
+                                       Modified (s, t, modified);
+                               }
+                       }
+                       // delayed, that way we show "Modified", "Added" and then "Removed"
+                       foreach (var item in removed) {
+                               SetContext (item);
+                               Removed (item);
+                       }
+                       // remaining == newly added in target
+                       if (target != null) {
+                               foreach (var item in target) {
+                                       SetContext (item);
+                                       Added (item, false);
+                               }
+                       }
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/ConstructorComparer.cs b/mcs/tools/mono-api-html/ConstructorComparer.cs
new file mode 100644 (file)
index 0000000..9bd837e
--- /dev/null
@@ -0,0 +1,148 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Reflection;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       // MethodComparer inherits from this one
+       public class ConstructorComparer : MemberComparer {
+
+               public override string GroupName {
+                       get { return "constructors"; }
+               }
+
+               public override string ElementName {
+                       get { return "constructor"; }
+               }
+
+               public override bool Find (XElement e)
+               {
+                       return (e.Attribute ("name").Value == Source.Attribute ("name").Value);
+               }
+
+               void RenderReturnType (XElement source, XElement target, ApiChange change)
+               {
+                       var srcType = source.GetTypeName ("returntype");
+                       var tgtType = target.GetTypeName ("returntype");
+
+                       if (srcType != tgtType) {
+                               change.AppendModified (srcType, tgtType, true);
+                               change.Append (" ");
+                       } else if (srcType != null) {
+                               // ctor don't have a return type
+                               change.Append (srcType);
+                               change.Append (" ");
+                       }
+               }
+
+               public override bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       if (base.Equals (source, target, changes))
+                               return true;
+                               
+                       var change = new ApiChange ();
+                       change.Header = "Modified " + GroupName;
+                       RenderMethodAttributes (source, target, change);
+                       RenderReturnType (source, target, change);
+                       RenderName (source, target, change);
+                       RenderGenericParameters (source, target, change);
+                       RenderParameters (source, target, change);
+
+                       changes.Add (source, target, change);
+
+                       return false;
+               }
+
+               public override string GetDescription (XElement e)
+               {
+                       var sb = new StringBuilder ();
+
+                       var attribs = e.Attribute ("attrib");
+                       if (attribs != null) {
+                               var attr = (MethodAttributes) Int32.Parse (attribs.Value);
+                               if ((attr & MethodAttributes.Public) != MethodAttributes.Public) {
+                                       sb.Append ("protected ");
+                               } else {
+                                       sb.Append ("public ");
+                               }
+
+                               if ((attr & MethodAttributes.Static) != 0) {
+                                       sb.Append ("static ");
+                               } else if ((attr & MethodAttributes.Virtual) != 0) {
+                                       if ((attr & MethodAttributes.VtableLayoutMask) == 0)
+                                               sb.Append ("override ");
+                                       else
+                                               sb.Append ("virtual ");
+                               }
+                       }
+
+                       string name = e.GetAttribute ("name");
+
+                       var r = e.GetTypeName ("returntype");
+                       if (r != null) {
+                               // ctor dont' have a return type
+                               sb.Append (r).Append (' ');
+                       } else {
+                               // show the constructor as it would be defined in C#
+                               name = name.Replace (".ctor", State.Type);
+                       }
+
+                       // the XML file `name` does not contain parameter names, so we must process them ourselves
+                       // which gives us the opportunity to simplify type names
+                       sb.Append (name.Substring (0, name.IndexOf ('(')));
+
+                       var genericp = e.Element ("generic-parameters");
+                       if (genericp != null) {
+                               var list = new List<string> ();
+                               foreach (var p in genericp.Elements ("generic-parameter")) {
+                                       list.Add (p.GetTypeName ("name"));
+                               }
+                               sb.Append ("&lt;").Append (String.Join (", ", list)).Append ("&gt;");
+                       }
+
+                       sb.Append (" (");
+                       var parameters = e.Element ("parameters");
+                       if (parameters != null) {
+                               var list = new List<string> ();
+                               foreach (var p in parameters.Elements ("parameter")) {
+                                       var pTypeName   = p.GetTypeName ("type");
+                                       list.Add (State.IgnoreParameterNameChanges
+                                               ? pTypeName
+                                               : pTypeName + " " + p.GetAttribute ("name"));
+                               }
+                               sb.Append (String.Join (", ", list));
+                       }
+                       sb.Append (");");
+
+                       return sb.ToString ();
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/EventComparer.cs b/mcs/tools/mono-api-html/EventComparer.cs
new file mode 100644 (file)
index 0000000..693f16f
--- /dev/null
@@ -0,0 +1,75 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class EventComparer : MemberComparer {
+
+               public override string GroupName {
+                       get { return "events"; }
+               }
+
+               public override string ElementName {
+                       get { return "event"; }
+               }
+
+               public override bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       if (base.Equals (source, target, changes))
+                               return true;
+
+                       var change = new ApiChange ();
+                       change.Header = "Modified " + GroupName;
+                       change.Append ("public event ");
+
+                       var srcEventType = source.GetTypeName ("eventtype");
+                       var tgtEventType = target.GetTypeName ("eventtype");
+
+                       if (srcEventType != tgtEventType) {
+                               change.AppendModified (srcEventType, tgtEventType, true);
+                       } else {
+                               change.Append (srcEventType);
+                       }
+                       change.Append (" ");
+                       change.Append (source.GetAttribute ("name")).Append (";");
+                       return false;
+               }
+
+               public override string GetDescription (XElement e)
+               {
+                       StringBuilder sb = new StringBuilder ();
+                       // TODO: attribs
+                       sb.Append ("public event ");
+                       sb.Append (e.GetTypeName ("eventtype")).Append (' ');
+                       sb.Append (e.GetAttribute ("name")).Append (';');
+                       return sb.ToString ();
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/FieldComparer.cs b/mcs/tools/mono-api-html/FieldComparer.cs
new file mode 100644 (file)
index 0000000..a2b0225
--- /dev/null
@@ -0,0 +1,211 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Reflection;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class FieldComparer : MemberComparer {
+
+               public override string GroupName {
+                       get { return "fields"; }
+               }
+
+               public override string ElementName {
+                       get { return "field"; }
+               }
+
+               void RenderFieldAttributes (FieldAttributes source, FieldAttributes target, ApiChange change)
+               {
+                       var srcNotSerialized = (source & FieldAttributes.NotSerialized) == FieldAttributes.NotSerialized;
+                       var tgtNotSerialized = (target & FieldAttributes.NotSerialized) == FieldAttributes.NotSerialized;
+                       if (srcNotSerialized != tgtNotSerialized) {
+                               // this is not a breaking change, so only render it if it changed.
+                               if (srcNotSerialized) {
+                                       change.AppendRemoved ("[NonSerialized]\n");
+                               } else {
+                                       change.AppendAdded ("[NonSerialized]\n");
+                               }
+                       }
+
+                       // the visibility values are the same for MethodAttributes and FieldAttributes, so just use the same method.
+                       RenderVisibility ((MethodAttributes) source, (MethodAttributes) target, change);
+                       // same for the static flag
+                       RenderStatic ((MethodAttributes) source, (MethodAttributes) target, change);
+
+                       var srcLiteral = (source & FieldAttributes.Literal) != 0;
+                       var tgtLiteral = (target & FieldAttributes.Literal) != 0;
+
+                       if (srcLiteral) {
+                               if (tgtLiteral) {
+                                       change.Append ("const ");
+                               } else {
+                                       change.AppendRemoved ("const", true).Append (" ");
+                               }
+                       } else if (tgtLiteral) {
+                               change.AppendAdded ("const", true).Append (" ");
+                       }
+
+                       var srcInitOnly = (source & FieldAttributes.InitOnly) != 0;
+                       var tgtInitOnly = (target & FieldAttributes.InitOnly) != 0;
+                       if (srcInitOnly) {
+                               if (tgtInitOnly) {
+                                       change.Append ("readonly ");
+                               } else {
+                                       change.AppendRemoved ("readonly", false).Append (" ");
+                               }
+                       } else if (tgtInitOnly) {
+                               change.AppendAdded ("readonly", true).Append (" ");
+                       }
+               }
+
+               public override bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       if (base.Equals (source, target, changes))
+                               return true;
+
+                       var name = source.GetAttribute ("name");
+                       var srcValue = source.GetAttribute ("value");
+                       var tgtValue = target.GetAttribute ("value");
+                       var change = new ApiChange ();
+                       change.Header = "Modified " + GroupName;
+
+                       if (State.BaseType == "System.Enum") {
+                               change.Append (name).Append (" = ");
+                               if (srcValue != tgtValue) {
+                                       change.AppendModified (srcValue, tgtValue, true);
+                               } else {
+                                       change.Append (srcValue);
+                               }
+                       } else {
+                               RenderFieldAttributes (source.GetFieldAttributes (), target.GetFieldAttributes (), change);
+
+                               var srcType = source.GetTypeName ("fieldtype");
+                               var tgtType = target.GetTypeName ("fieldtype");
+
+                               if (srcType != tgtType) {
+                                       change.AppendModified (srcType, tgtType, true);
+                               } else {
+                                       change.Append (srcType);
+                               }
+                               change.Append (" ");
+                               change.Append (name);
+
+                               if (srcType == "string" && srcValue != null)
+                                       srcValue = "\"" + srcValue + "\"";
+
+                               if (tgtType == "string" && tgtValue != null)
+                                       tgtValue = "\"" + tgtValue + "\"";
+
+                               if (srcValue != tgtValue) {
+                                       change.Append (" = ");
+                                       if (srcValue == null)
+                                               srcValue = "null";
+                                       if (tgtValue == null)
+                                               tgtValue = "null";
+                                       change.AppendModified (srcValue, tgtValue, true);
+                               } else if (srcValue != null) {
+                                       change.Append (" = ");
+                                       change.Append (srcValue);
+                               }
+                               change.Append (";");
+                       }
+
+                       changes.Add (source, target, change);
+
+                       return false;
+               }
+
+               public override string GetDescription (XElement e)
+               {
+                       var sb = new StringBuilder ();
+
+                       string name = e.GetAttribute ("name");
+                       string value = e.GetAttribute ("value");
+
+                       if (State.BaseType == "System.Enum") {
+                               sb.Append (name).Append (" = ").Append (value).Append (',');
+                       } else {
+                               var attribs = e.Attribute ("attrib");
+                               if (attribs != null) {
+                                       var attr = (FieldAttributes)Int32.Parse (attribs.Value);
+                                       if ((attr & FieldAttributes.Public) != FieldAttributes.Public) {
+                                               sb.Append ("protected ");
+                                       } else {
+                                               sb.Append ("public ");
+                                       }
+
+                                       if ((attr & FieldAttributes.Static) != 0)
+                                               sb.Append ("static ");
+
+                                       if ((attr & FieldAttributes.Literal) != 0)
+                                               sb.Append ("const ");
+                               }
+
+                               string ftype = e.GetTypeName ("fieldtype");
+                               sb.Append (ftype).Append (' ');
+                               sb.Append (name);
+                               if (ftype == "string" && e.Attribute ("value") != null) {
+                                       if (value == null)
+                                               sb.Append (" = null");
+                                       else
+                                               sb.Append (" = \"").Append (value).Append ('"');
+                               }
+                               sb.Append (';');
+                       }
+
+                       return sb.ToString ();
+               }
+
+               public override void BeforeAdding (IEnumerable<XElement> list)
+               {
+                       first = true;
+                       if (State.BaseType == "System.Enum") {
+                               Output.WriteLine ("<div>");
+                               Output.WriteLine ("<p>Added value{0}:</p>", list.Count () > 1 ? "s" : String.Empty);
+                               Output.WriteLine ("<pre class='added' data-is-non-breaking>");
+                       } else {
+                               base.BeforeAdding (list);
+                       }
+               }
+
+               public override void BeforeRemoving (IEnumerable<XElement> list)
+               {
+                       first = true;
+                       if (State.BaseType == "System.Enum") {
+                               Output.WriteLine ("<p>Removed value{0}:</p>", list.Count () > 1 ? "s" : String.Empty);
+                               Output.WriteLine ("<pre class='removed' data-is-breaking>");
+                       } else {
+                               base.BeforeRemoving (list);
+                       }
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/Helpers.cs b/mcs/tools/mono-api-html/Helpers.cs
new file mode 100644 (file)
index 0000000..8769785
--- /dev/null
@@ -0,0 +1,207 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Reflection;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public static class Helper {
+               public static bool IsTrue (this XElement self, string name)
+               {
+                       return (self.GetAttribute (name) == "true");
+               }
+
+               public static string GetAttribute (this XElement self, string name)
+               {
+                       var n = self.Attribute (name);
+                       if (n == null)
+                               return null;
+                       return n.Value;
+               }
+
+               // null == no obsolete, String.Empty == no description
+               public static string GetObsoleteMessage (this XElement self)
+               {
+                       var cattrs = self.Element ("attributes");
+                       if (cattrs == null)
+                               return null;
+
+                       foreach (var ca in cattrs.Elements ("attribute")) {
+                               if (ca.GetAttribute ("name") != "System.ObsoleteAttribute")
+                                       continue;
+                               var props = ca.Element ("properties");
+                               if (props == null)
+                                       return String.Empty; // no description
+                               foreach (var p in props.Elements ("property")) {
+                                       if (p.GetAttribute ("name") != "Message")
+                                               continue;
+                                       return p.GetAttribute ("value");
+                               }
+                       }
+                       return null;
+               }
+
+               public static IEnumerable<XElement> Descendants (this XElement self, params string[] names)
+               {
+                       XElement el = self;
+                       if (el == null)
+                               return null;
+
+                       for (int i = 0; i < names.Length - 1; i++) {
+                               el = el.Element (names [i]);
+                               if (el == null)
+                                       return null;
+                       }
+                       return el.Elements (names [names.Length - 1]);
+               }
+
+               public static List<XElement> DescendantList (this XElement self, params string[] names)
+               {
+                       var descendants = self.Descendants (names);
+                       if (descendants == null)
+                               return null;
+                       return descendants.ToList ();
+               }
+
+               // make it beautiful (.NET -> C#)
+               public static string GetTypeName (this XElement self, string name)
+               {
+                       string type = self.GetAttribute (name);
+                       if (type == null)
+                               return null;
+
+                       StringBuilder sb = null;
+                       bool is_nullable = false;
+                       if (type.StartsWith ("System.Nullable`1[", StringComparison.Ordinal)) {
+                               is_nullable = true;
+                               sb = new StringBuilder (type, 18, type.Length - 19, 1024);
+                       } else {
+                               sb = new StringBuilder (type);
+                       }
+
+                       bool is_ref = (sb [sb.Length - 1] == '&');
+                       if (is_ref)
+                               sb.Remove (sb.Length - 1, 1);
+
+                       int array = 0;
+                       while ((sb [sb.Length - 1] == ']') && (sb [sb.Length - 2] == '[')) {
+                               sb.Remove (sb.Length - 2, 2);
+                               array++;
+                       }
+
+                       bool is_pointer = (sb [sb.Length - 1] == '*');
+                       if (is_pointer)
+                               sb.Remove (sb.Length - 1, 1);
+
+                       type = GetTypeName (sb.Replace ('+', '.').ToString ());
+                       sb.Length = 0;
+                       if (is_ref)
+                               sb.Append (self.GetAttribute ("direction")).Append (' ');
+
+                       sb.Append (type);
+
+                       while (array-- > 0)
+                               sb.Append ("[]");
+                       if (is_nullable)
+                               sb.Append ('?');
+                       if (is_pointer)
+                               sb.Append ('*');
+                       return sb.ToString ();
+               }
+
+               static string GetTypeName (string type)
+               {
+                       int pos = type.IndexOf ('`');
+                       if (pos >= 0) {
+                               int end = type.LastIndexOf (']');
+                               string subtype = type.Substring (pos + 3, end - pos - 3);
+                               return type.Substring (0, pos) + "&lt;" + GetTypeName (subtype) + "&gt;";
+                       }
+
+                       switch (type) {
+                       case "System.String":
+                               return "string";
+                       case "System.Int32":
+                               return "int";
+                       case "System.UInt32":
+                               return "uint";
+                       case "System.Int64":
+                               return "long";
+                       case "System.UInt64":
+                               return "ulong";
+                       case "System.Void":
+                               return "void";
+                       case "System.Boolean":
+                               return "bool";
+                       case "System.Object":
+                               return "object";
+                       case "System.Single":
+                               return "float";
+                       case "System.Double":
+                               return "double";
+                       case "System.Byte":
+                               return "byte";
+                       case "System.SByte":
+                               return "sbyte";
+                       case "System.Int16":
+                               return "short";
+                       case "System.UInt16":
+                               return "ushort";
+                       case "System.Char":
+                               return "char";
+                       case "System.nint":
+                               return "nint";
+                       case "System.nuint":
+                               return "uint";
+                       case "System.nfloat":
+                               return "nfloat";
+                       case "System.IntPtr":
+                               return "IntPtr";
+                       default:
+                               if (type.StartsWith (State.Namespace, StringComparison.Ordinal))
+                                       type = type.Substring (State.Namespace.Length + 1);
+                               return type;
+                       }
+               }
+
+               public static MethodAttributes GetMethodAttributes (this XElement element)
+               {
+                       var srcAttribs = element.Attribute ("attrib");
+                       return (MethodAttributes) (srcAttribs != null ? Int32.Parse (srcAttribs.Value) : 0);
+               }
+
+               public static FieldAttributes GetFieldAttributes (this XElement element)
+               {
+                       var srcAttribs = element.Attribute ("attrib");
+                       return (FieldAttributes) (srcAttribs != null ? Int32.Parse (srcAttribs.Value) : 0);
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/InterfaceComparer.cs b/mcs/tools/mono-api-html/InterfaceComparer.cs
new file mode 100644 (file)
index 0000000..df52f16
--- /dev/null
@@ -0,0 +1,47 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class InterfaceComparer : MemberComparer {
+
+               public override string GroupName {
+                       get { return "interfaces"; }
+               }
+
+               public override string ElementName {
+                       get { return "interface"; }
+               }
+
+               public override string GetDescription (XElement e)
+               {
+                       return e.GetTypeName ("name");
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/Makefile b/mcs/tools/mono-api-html/Makefile
new file mode 100644 (file)
index 0000000..e1c55c1
--- /dev/null
@@ -0,0 +1,10 @@
+thisdir = tools/mono-api-html
+SUBDIRS =
+include ../../build/rules.make
+
+LIB_REFS = Mono.Cecil System.Xml System.Core System System.Xml.Linq
+LOCAL_MCS_FLAGS =
+
+PROGRAM = mono-api-html.exe
+
+include ../../build/executable.make
diff --git a/mcs/tools/mono-api-html/MemberComparer.cs b/mcs/tools/mono-api-html/MemberComparer.cs
new file mode 100644 (file)
index 0000000..d12d866
--- /dev/null
@@ -0,0 +1,608 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013-2014 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Reflection;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public abstract class MemberComparer : Comparer {
+
+               // true if this is the first element being added or removed in the group being rendered
+               protected bool first;
+
+               public abstract string GroupName { get; }
+               public abstract string ElementName { get; }
+
+               protected virtual bool IsBreakingRemoval (XElement e)
+               {
+                       return true;
+               }
+
+               public void Compare (XElement source, XElement target)
+               {
+                       var s = source.Element (GroupName);
+                       var t = target.Element (GroupName);
+                       if (XNode.DeepEquals (s, t))
+                               return;
+
+                       if (s == null) {
+                               Add (t.Elements (ElementName));
+                       } else if (t == null) {
+                               Remove (s.Elements (ElementName));
+                       } else {
+                               Compare (s.Elements (ElementName), t.Elements (ElementName));
+                       }
+               }
+
+               public override void SetContext (XElement current)
+               {
+               }
+
+               string GetContainingType (XElement el)
+               {
+                       return el.Ancestors ("class").First ().Attribute ("type").Value;
+               }
+
+               bool IsInInterface (XElement el)
+               {
+                       return GetContainingType (el) == "interface";
+               }
+
+               public XElement Source { get; set; }
+
+               public virtual bool Find (XElement e)
+               {
+                       return e.GetAttribute ("name") == Source.GetAttribute ("name");
+               }
+
+               XElement Find (IEnumerable<XElement> target)
+               {
+                       return State.Lax ? target.FirstOrDefault (Find) : target.SingleOrDefault (Find);
+               }
+
+               public override void Compare (IEnumerable<XElement> source, IEnumerable<XElement> target)
+               {
+                       removed.Clear ();
+                       modified.Clear ();
+
+                       foreach (var s in source) {
+                               SetContext (s);
+                               Source = s;
+                               var t = Find (target);
+                               if (t == null) {
+                                       // not in target, it was removed
+                                       removed.Add (s);
+                               } else {
+                                       t.Remove ();
+                                       // possibly modified
+                                       if (Equals (s, t, modified))
+                                               continue;
+
+                                       Modified (s, t, modified);
+                               }
+                       }
+                       // delayed, that way we show "Modified", "Added" and then "Removed"
+                       Remove (removed);
+
+                       Modify (modified);
+
+                       // remaining == newly added in target
+                       Add (target);
+               }
+
+               void Add (IEnumerable<XElement> elements)
+               {
+                       bool a = false;
+                       foreach (var item in elements) {
+                               SetContext (item);
+                               if (State.IgnoreAdded.Any (re => re.IsMatch (GetDescription (item))))
+                                       continue;
+                               if (!a) {
+                                       BeforeAdding (elements);
+                                       a = true;
+                               }
+                               Added (item, false);
+                       }
+                       if (a)
+                               AfterAdding ();
+               }
+
+               void Modify (ApiChanges modified)
+               {
+                       foreach (var changes in modified) {
+                               Output.WriteLine ("<p>{0}:</p>", changes.Key);
+                               Output.WriteLine ("<pre>");
+                               foreach (var element in changes.Value) {
+                                       Output.Write ("<div {0}>", element.Breaking ? "data-is-breaking" : "data-is-non-breaking");
+                                       foreach (var line in element.Member.ToString ().Split ('\n'))
+                                               Output.WriteLine ("\t{0}", line);
+                                       Output.Write ("</div>");
+
+                               }
+                               Output.WriteLine ("</pre>");
+                       }
+               }
+
+               void Remove (IEnumerable<XElement> elements)
+               {
+                       bool r = false;
+                       foreach (var item in elements) {
+                               if (State.IgnoreRemoved.Any (re => re.IsMatch (GetDescription (item))))
+                                       continue;
+                               SetContext (item);
+                               if (!r) {
+                                       BeforeRemoving (elements);
+                                       r = true;
+                               }
+                               Removed (item);
+                       }
+                       if (r)
+                               AfterRemoving ();
+               }
+                       
+               public abstract string GetDescription (XElement e);
+
+               protected StringBuilder GetObsoleteMessage (XElement e)
+               {
+                       var sb = new StringBuilder ();
+                       string o = e.GetObsoleteMessage ();
+                       if (o != null) {
+                               sb.Append ("[Obsolete");
+                               if (o.Length > 0)
+                                       sb.Append (" (\"").Append (o).Append ("\")");
+                               sb.AppendLine ("]");
+                               for (int i = 0; i < State.Indent + 1; i++)
+                                       sb.Append ('\t');
+                       }
+                       return sb;
+               }
+
+               public override bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       RenderAttributes (source, target, changes);
+
+                       // We don't want to compare attributes.
+                       RemoveAttributes (source);
+                       RemoveAttributes (target);
+
+                       return base.Equals (source, target, changes);
+               }
+
+               public virtual void BeforeAdding (IEnumerable<XElement> list)
+               {
+                       first = true;
+                       Output.WriteLine ("<div>");
+                       Output.WriteLine ("<p>Added {0}:</p>", list.Count () > 1 ? GroupName : ElementName);
+                       Output.WriteLine ("<pre>");
+               }
+
+               public override void Added (XElement target, bool wasParentAdded)
+               {
+                       var o = GetObsoleteMessage (target);
+                       if (!first && (o.Length > 0))
+                               Output.WriteLine ();
+                       Indent ();
+                       bool isInterfaceBreakingChange = !wasParentAdded && IsInInterface (target);
+                       Output.Write ("\t<span class='added added-{0} {1}' {2}>", ElementName, isInterfaceBreakingChange ? "breaking" : string.Empty, isInterfaceBreakingChange ? "data-is-breaking" : "data-is-non-breaking");
+                       Output.Write ("{0}{1}", o, GetDescription (target));
+                       Output.WriteLine ("</span>");
+                       first = false;
+               }
+
+               public virtual void AfterAdding ()
+               {
+                       Output.WriteLine ("</pre>");
+                       Output.WriteLine ("</div>");
+               }
+
+               public override void Modified (XElement source, XElement target, ApiChanges change)
+               {
+               }
+
+               public virtual void BeforeRemoving (IEnumerable<XElement> list)
+               {
+                       first = true;
+                       Output.WriteLine ("<p>Removed {0}:</p>\n", list.Count () > 1 ? GroupName : ElementName);
+                       Output.WriteLine ("<pre>");
+               }
+
+               public override void Removed (XElement source)
+               {
+                       var o = GetObsoleteMessage (source);
+                       if (!first && (o.Length > 0))
+                               Output.WriteLine ();
+
+                       bool is_breaking = IsBreakingRemoval (source);
+
+                       Indent ();
+                       Output.Write ("\t<span class='removed removed-{0} {2}' {1}>", ElementName, is_breaking ? "data-is-breaking" : "data-is-non-breaking", is_breaking ? "breaking" : string.Empty);
+                       Output.Write ("{0}{1}", o, GetDescription (source));
+                       Output.WriteLine ("</span>");
+                       first = false;
+               }
+
+               public virtual void AfterRemoving ()
+               {
+                       Output.WriteLine ("</pre>");;
+               }
+
+               string RenderGenericParameter (XElement gp)
+               {
+                       var sb = new StringBuilder ();
+                       sb.Append (gp.GetTypeName ("name"));
+
+                       var constraints = gp.DescendantList ("generic-parameter-constraints", "generic-parameter-constraint");
+                       if (constraints != null && constraints.Count > 0) {
+                               sb.Append (" : ");
+                               for (int i = 0; i < constraints.Count; i++) {
+                                       if (i > 0)
+                                               sb.Append (", ");
+                                       sb.Append (constraints [i].GetTypeName ("name"));
+                               }
+                       }
+                       return sb.ToString ();
+               }
+
+               protected void RenderGenericParameters (XElement source, XElement target, ApiChange change)
+               {
+                       var src = source.DescendantList ("generic-parameters", "generic-parameter");
+                       var tgt = target.DescendantList ("generic-parameters", "generic-parameter");
+                       var srcCount = src == null ? 0 : src.Count;
+                       var tgtCount = tgt == null ? 0 : tgt.Count;
+
+                       if (srcCount == 0 && tgtCount == 0)
+                               return;
+
+                       change.Append ("&lt;");
+                       for (int i = 0; i < Math.Max (srcCount, tgtCount); i++) {
+                               if (i > 0)
+                                       change.Append (", ");
+                               if (i >= srcCount) {
+                                       change.AppendAdded (RenderGenericParameter (tgt [i]), true);
+                               } else if (i >= tgtCount) {
+                                       change.AppendRemoved (RenderGenericParameter (src [i]), true);
+                               } else {
+                                       var srcName = RenderGenericParameter (src [i]);
+                                       var tgtName = RenderGenericParameter (tgt [i]);
+
+                                       if (srcName != tgtName) {
+                                               change.AppendModified (srcName, tgtName, true);
+                                       } else {
+                                               change.Append (srcName);
+                                       }
+                                       }
+                               }
+                       change.Append ("&gt;");
+               }
+
+               protected string FormatValue (string type, string value)
+               {
+                       if (value == null)
+                               return "null";
+
+                       if (type == "string")
+                               return "\"" + value + "\"";
+                       else if (type == "bool") {
+                               switch (value) {
+                               case "True":
+                                       return "true";
+                               case "False":
+                                       return "false";
+                               default:
+                                       return value;
+                               }
+                       }
+
+                       return value;
+               }
+
+               protected void RenderParameters (XElement source, XElement target, ApiChange change)
+               {
+                       var src = source.DescendantList ("parameters", "parameter");
+                       var tgt = target.DescendantList ("parameters", "parameter");
+                       var srcCount = src == null ? 0 : src.Count;
+                       var tgtCount = tgt == null ? 0 : tgt.Count;
+
+                       change.Append (" (");
+                       for (int i = 0; i < Math.Max (srcCount, tgtCount); i++) {
+                               if (i > 0)
+                                       change.Append (", ");
+
+                               if (i >= srcCount) {
+                                       change.AppendAdded (tgt [i].GetTypeName ("type") + " " + tgt [i].GetAttribute ("name"), true);
+                               } else if (i >= tgtCount) {
+                                       change.AppendRemoved (src [i].GetTypeName ("type") + " " + src [i].GetAttribute ("name"), true);
+                               } else {
+                                       var paramSourceType = src [i].GetTypeName ("type");
+                                       var paramTargetType = tgt [i].GetTypeName ("type");
+
+                                       var paramSourceName = src [i].GetAttribute ("name");
+                                       var paramTargetName = tgt [i].GetAttribute ("name");
+
+                                       if (paramSourceType != paramTargetType) {
+                                               change.AppendModified (paramSourceType, paramTargetType, true);
+                                       } else {
+                                               change.Append (paramSourceType);
+                                       }
+                                       change.Append (" ");
+                                       if (paramSourceName != paramTargetName) {
+                                               change.AppendModified (paramSourceName, paramTargetName, false);
+                                       } else {
+                                               change.Append (paramSourceName);
+                                       }
+
+                                       var optSource = src [i].Attribute ("optional");
+                                       var optTarget = tgt [i].Attribute ("optional");
+                                       var srcValue = FormatValue (paramSourceType, src [i].GetAttribute ("defaultValue"));
+                                       var tgtValue = FormatValue (paramTargetType, tgt [i].GetAttribute ("defaultValue"));
+
+                                       if (optSource != null) {
+                                               if (optTarget != null) {
+                                                       change.Append (" = ");
+                                                       if (srcValue != tgtValue) {
+                                                               change.AppendModified (srcValue, tgtValue, false);
+                                                       } else {
+                                                               change.Append (tgtValue);
+                                                       }
+                                               } else {
+                                                       change.AppendRemoved (" = " + srcValue);
+                                               }
+                                       } else {
+                                               if (optTarget != null)
+                                                       change.AppendAdded (" = " + tgtValue);
+                                       }
+                               }
+                       }
+
+                       change.Append (")");
+
+                       // Ignore any parameter name changes if requested.
+                       if (State.IgnoreParameterNameChanges && !change.Breaking) {
+                               change.AnyChange = false;
+                               change.HasIgnoredChanges = true;
+                       }
+               }
+
+               void RenderVTable (MethodAttributes source, MethodAttributes target, ApiChange change)
+               {
+                       var srcAbstract = (source & MethodAttributes.Abstract) == MethodAttributes.Abstract;
+                       var tgtAbstract = (target & MethodAttributes.Abstract) == MethodAttributes.Abstract;
+                       var srcFinal = (source & MethodAttributes.Final) == MethodAttributes.Final;
+                       var tgtFinal = (target & MethodAttributes.Final) == MethodAttributes.Final;
+                       var srcVirtual = (source & MethodAttributes.Virtual) == MethodAttributes.Virtual;
+                       var tgtVirtual = (target & MethodAttributes.Virtual) == MethodAttributes.Virtual;
+                       var srcOverride = (source & MethodAttributes.VtableLayoutMask) != MethodAttributes.NewSlot;
+                       var tgtOverride = (target & MethodAttributes.VtableLayoutMask) != MethodAttributes.NewSlot;
+
+                       var srcWord = srcVirtual ? (srcOverride ? "override" : "virtual") : string.Empty;
+                       var tgtWord = tgtVirtual ? (tgtOverride ? "override" : "virtual") : string.Empty;
+                       var breaking = srcWord.Length > 0 && tgtWord.Length == 0;
+
+                       if (srcAbstract) {
+                               if (tgtAbstract) {
+                                       change.Append ("abstract ");
+                               } else if (tgtVirtual) {
+                                       change.AppendModified ("abstract", tgtWord, false).Append (" ");
+                               } else {
+                                       change.AppendRemoved ("abstract").Append (" ");
+                               }
+                       } else {
+                               if (tgtAbstract) {
+                                       change.AppendAdded ("abstract", true).Append (" ");
+                               } else if (srcWord != tgtWord) {
+                                       if (!tgtFinal)
+                                               change.AppendModified (srcWord, tgtWord, breaking).Append (" ");
+                               } else if (tgtWord.Length > 0) {
+                                       change.Append (tgtWord).Append (" ");
+                               } else if (srcWord.Length > 0) {
+                                       change.AppendRemoved (srcWord, breaking).Append (" ");
+                               }
+                       }
+
+                       if (srcFinal) {
+                               if (tgtFinal) {
+                                       change.Append ("final ");
+                               } else {
+                                       change.AppendRemoved ("final", false).Append (" "); // removing 'final' is not a breaking change.
+                               }
+                       } else {
+                               if (tgtFinal && srcVirtual) {
+                                       change.AppendModified ("virtual", "final", true).Append (" "); // adding 'final' is a breaking change if the member was virtual
+                               }
+                       }
+
+                       if (!srcVirtual && !srcFinal && tgtVirtual && tgtFinal) {
+                               // existing member implements a member from a new interface
+                               // this would show up as 'virtual final', which is redundant, so show nothing at all.
+                               change.HasIgnoredChanges = true;
+                       }
+
+                       // Ignore non-breaking virtual changes.
+                       if (State.IgnoreVirtualChanges && !change.Breaking) {
+                               change.AnyChange = false;
+                               change.HasIgnoredChanges = true;
+                       }
+
+                       var tgtSecurity = (source & MethodAttributes.HasSecurity) == MethodAttributes.HasSecurity;
+                       var srcSecurity = (target & MethodAttributes.HasSecurity) == MethodAttributes.HasSecurity;
+
+                       if (tgtSecurity != srcSecurity)
+                               change.HasIgnoredChanges = true;
+
+                       var srcPInvoke = (source & MethodAttributes.PinvokeImpl) == MethodAttributes.PinvokeImpl;
+                       var tgtPInvoke = (target & MethodAttributes.PinvokeImpl) == MethodAttributes.PinvokeImpl;
+                       if (srcPInvoke != tgtPInvoke)
+                               change.HasIgnoredChanges = true;
+               }
+
+               protected string GetVisibility (MethodAttributes attr)
+               {
+                       switch (attr) {
+                       case MethodAttributes.Private:
+                       case MethodAttributes.PrivateScope:
+                               return "private";
+                       case MethodAttributes.Assembly:
+                               return "internal";
+                       case MethodAttributes.FamANDAssem:
+                               return "private internal";
+                       case MethodAttributes.FamORAssem:
+                               return "protected"; // customers don't care about 'internal';
+                       case MethodAttributes.Family:
+                               return "protected";
+                       case MethodAttributes.Public:
+                               return "public";
+                       default:
+                               throw new NotImplementedException ();
+                       }
+               }
+
+               protected void RenderVisibility (MethodAttributes source, MethodAttributes target, ApiChange diff)
+               {
+                       source = source & MethodAttributes.MemberAccessMask;
+                       target = target & MethodAttributes.MemberAccessMask;
+
+                       if (source == target) {
+                               diff.Append (GetVisibility (target));
+                       } else {
+                               var breaking = false;
+                               switch (source) {
+                               case MethodAttributes.Private:
+                               case MethodAttributes.Assembly:
+                               case MethodAttributes.FamANDAssem:
+                                       break; // these are not publicly visible, thus not breaking
+                               case MethodAttributes.FamORAssem:
+                               case MethodAttributes.Family:
+                                       switch (target) {
+                                       case MethodAttributes.Public:
+                                               // to public is not a breaking change
+                                               break;
+                                       case MethodAttributes.Family:
+                                       case MethodAttributes.FamORAssem:
+                                               // not a breaking change, but should still show up in diff
+                                               break;
+                                       default:
+                                               // anything else is a breaking change
+                                               breaking = true;
+                                               break;
+                                       }
+                                       break;
+                               case MethodAttributes.Public:
+                               default:
+                                       // any change from public is breaking.
+                                       breaking = true;
+                                       break;
+                               }
+
+                               diff.AppendModified (GetVisibility (source), GetVisibility (target), breaking);
+                       }
+                       diff.Append (" ");
+               }
+
+               protected void RenderStatic (MethodAttributes src, MethodAttributes tgt, ApiChange diff)
+               {
+                       var srcStatic = (src & MethodAttributes.Static) == MethodAttributes.Static;
+                       var tgtStatic = (tgt & MethodAttributes.Static) == MethodAttributes.Static;
+
+                       if (srcStatic != tgtStatic) {
+                               if (srcStatic) {
+                                       diff.AppendRemoved ("static", true).Append (" ");
+                               } else {
+                                       diff.AppendAdded ("static", true).Append (" ");
+                               }
+                       }
+               }
+
+               protected void RenderMethodAttributes (MethodAttributes src, MethodAttributes tgt, ApiChange diff)
+               {
+                       RenderStatic (src, tgt, diff);
+                       RenderVisibility (src & MethodAttributes.MemberAccessMask, tgt & MethodAttributes.MemberAccessMask, diff);
+                       RenderVTable (src, tgt, diff);
+               }
+
+               protected void RenderMethodAttributes (XElement source, XElement target, ApiChange diff)
+               {
+                       RenderMethodAttributes (source.GetMethodAttributes (), target.GetMethodAttributes (), diff);
+               }
+
+               protected void RemoveAttributes (XElement element)
+               {
+                       var srcAttributes = element.Element ("attributes");
+                       if (srcAttributes != null)
+                               srcAttributes.Remove ();
+
+                       foreach (var el in element.Elements ())
+                               RemoveAttributes (el);
+               }
+
+               protected void RenderAttributes (XElement source, XElement target, ApiChanges changes)
+               {
+                       var srcObsolete = source.GetObsoleteMessage ();
+                       var tgtObsolete = target.GetObsoleteMessage ();
+
+                       if (srcObsolete == tgtObsolete)
+                               return; // nothing changed
+
+                       if (srcObsolete == null) {
+                               if (tgtObsolete == null)
+                                       return; // neither is obsolete
+                               var change = new ApiChange ();
+                               change.Header = "Obsoleted " + GroupName;
+                               change.Append (string.Format ("<span class='obsolete obsolete-{0}' data-is-non-breaking>", ElementName));
+                               change.Append ("[Obsolete (");
+                               if (tgtObsolete != string.Empty)
+                                       change.Append ("\"").Append (tgtObsolete).Append ("\"");
+                               change.Append (")]\n");
+                               change.Append (GetDescription (target));
+                               change.Append ("</span>");
+                               change.AnyChange = true;
+                               changes.Add (source, target, change);
+                       } else if (tgtObsolete == null) {
+                               // Made non-obsolete. Do we care to report this?
+                       } else {
+                               // Obsolete message changed. Do we care to report this?
+                       }
+               }
+
+               protected void RenderName (XElement source, XElement target, ApiChange change)
+               {
+                       var name = target.GetAttribute ("name");
+                       // show the constructor as it would be defined in C#
+                       name = name.Replace (".ctor", State.Type);
+
+                       var p = name.IndexOf ('(');
+                       if (p >= 0)
+                               name = name.Substring (0, p);
+
+                       change.Append (name);
+               }
+
+       }
+}
diff --git a/mcs/tools/mono-api-html/MethodComparer.cs b/mcs/tools/mono-api-html/MethodComparer.cs
new file mode 100644 (file)
index 0000000..4c893e7
--- /dev/null
@@ -0,0 +1,77 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Linq;
+using System.Reflection;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class MethodComparer : ConstructorComparer {
+
+               public override string GroupName {
+                       get { return "methods"; }
+               }
+
+               public override string ElementName {
+                       get { return "method"; }
+               }
+
+               // operators have identical names but vary by return types
+               public override bool Find (XElement e)
+               {
+                       if (e.GetAttribute ("name") != Source.GetAttribute ("name"))
+                               return false;
+
+                       if (e.GetAttribute ("returntype") != Source.GetAttribute ("returntype"))
+                               return false;
+
+                       var eGP = e.Element ("generic-parameters");
+                       var sGP = Source.Element ("generic-parameters");
+
+                       if (eGP == null && sGP == null)
+                               return true;
+                       else if (eGP == null ^ sGP == null)
+                               return false;
+                       else {
+                               var eGPs = eGP.Elements ("generic-parameter");
+                               var sGPs = sGP.Elements ("generic-parameter");
+                               return eGPs.Count () == sGPs.Count ();
+                       }
+               }
+
+               protected override bool IsBreakingRemoval (XElement e)
+               {
+                       // Removing virtual methods that override another method is not a breaking change.
+                       var is_override = e.Attribute ("is-override");
+                       if (is_override != null)
+                               return is_override.Value != "true";
+                       
+                       return true; // all other removals are breaking changes
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/NamespaceComparer.cs b/mcs/tools/mono-api-html/NamespaceComparer.cs
new file mode 100644 (file)
index 0000000..063e34e
--- /dev/null
@@ -0,0 +1,104 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class NamespaceComparer : Comparer {
+
+               ClassComparer comparer;
+
+               public NamespaceComparer ()
+               {
+                       comparer =  new ClassComparer ();
+               }
+
+               public void Compare (XElement source, XElement target)
+               {
+                       var s = source.Element ("namespaces");
+                       var t = target.Element ("namespaces");
+                       if (XNode.DeepEquals (s, t))
+                               return;
+                       Compare (s.Elements ("namespace"), t.Elements ("namespace"));
+               }
+
+               public override void SetContext (XElement current)
+               {
+                       State.Namespace = current.Attribute ("name").Value;
+               }
+
+               public override void Added (XElement target, bool wasParentAdded)
+               {
+                       string name = target.Attribute ("name").Value;
+                       if (State.IgnoreNew.Any (re => re.IsMatch (name)))
+                               return;
+
+                       Output.WriteLine ("<!-- start namespace {0} --> <div> ", name);
+                       Output.WriteLine ("<h2>New Namespace {0}</h2>", name);
+                       Output.WriteLine ();
+                       // list all new types
+                       foreach (var addedType in target.Element ("classes").Elements ("class"))
+                               comparer.Added (addedType, true);
+                       Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
+                       Output.WriteLine ();
+               }
+
+               public override void Modified (XElement source, XElement target, ApiChanges differences)
+               {
+                       var output = Output;
+                       State.Output = new StringWriter ();
+                       comparer.Compare (source, target);
+
+                       var s = Output.ToString ();
+                       State.Output = output;
+                       if (s.Length > 0) {
+                               var name = target.Attribute ("name").Value;
+                               Output.WriteLine ("<!-- start namespace {0} --> <div> ", name);
+                               Output.WriteLine ("<h2>Namespace {0}</h2>", name);
+                               Output.WriteLine (s);
+                               Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
+                       }
+               }
+
+               public override void Removed (XElement source)
+               {
+                       var name = source.Attribute ("name").Value;
+                       Output.WriteLine ("<!-- start namespace {0} --> <div>", name);
+                       Output.WriteLine ("<h2>Removed Namespace {0}</h2>", name);
+                       Output.WriteLine ();
+                       // list all removed types
+                       foreach (var removedType in source.Element ("classes").Elements ("class"))
+                               comparer.Removed (removedType);
+                       Output.WriteLine ("</div> <!-- end namespace {0} -->", name);
+                       Output.WriteLine ();
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/PropertyComparer.cs b/mcs/tools/mono-api-html/PropertyComparer.cs
new file mode 100644 (file)
index 0000000..f51dd23
--- /dev/null
@@ -0,0 +1,254 @@
+// 
+// Authors
+//    Sebastien Pouliot  <sebastien@xamarin.com>
+//
+// Copyright 2013 Xamarin Inc. http://www.xamarin.com
+// 
+// Permission is hereby granted, free of charge, to any person obtaining
+// a copy of this software and associated documentation files (the
+// "Software"), to deal in the Software without restriction, including
+// without limitation the rights to use, copy, modify, merge, publish,
+// distribute, sublicense, and/or sell copies of the Software, and to
+// permit persons to whom the Software is furnished to do so, subject to
+// the following conditions:
+//
+// The above copyright notice and this permission notice shall be
+// included in all copies or substantial portions of the Software.
+//
+// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
+// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
+// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
+// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+//
+
+using System;
+using System.Collections.Generic;
+using System.Reflection;
+using System.Text;
+using System.Xml.Linq;
+
+namespace Xamarin.ApiDiff {
+
+       public class PropertyComparer : MemberComparer {
+
+               public override string GroupName {
+                       get { return "properties"; }
+               }
+
+               public override string ElementName {
+                       get { return "property"; }
+               }
+
+               public override bool Find (XElement e)
+               {
+                       if (!base.Find (e))
+                               return false;
+                       // the same Item (indexer) property can have different parameters
+                       return e.GetAttribute ("params") == Source.GetAttribute ("params");
+               }
+
+               void GetAccessors (XElement element, out XElement getter, out XElement setter)
+               {
+                       var methods = element.Element ("methods");
+
+                       getter = null;
+                       setter = null;
+
+                       if (methods == null)
+                               return;
+                               
+                       foreach (var m in methods.Elements ("method")) {
+                               var n = m.GetAttribute ("name");
+                               if (n.StartsWith ("get_", StringComparison.Ordinal)) {
+                                       getter = m;
+                               } else if (n.StartsWith ("set_", StringComparison.Ordinal)) {
+                                       setter = m;
+                               }
+                       }
+               }
+
+               MethodAttributes GetMethodAttributes (XElement getter, XElement setter)
+               {
+                       if (getter == null)
+                               return setter.GetMethodAttributes ();
+                       else if (setter == null)
+                               return getter.GetMethodAttributes ();
+
+                       var gAttr = getter.GetMethodAttributes ();
+                       var sAttr = setter.GetMethodAttributes ();
+                       var g = gAttr & MethodAttributes.MemberAccessMask;
+                       var s = sAttr & MethodAttributes.MemberAccessMask;
+                       // Visibility is ordered numerically (higher value = more visible).
+                       // We want the most visible.
+                       var visibility = (MethodAttributes) Math.Max ((int) g, (int) s);
+                       // Do a bitwise or with the rest of the flags
+                       var g_no_visibility = gAttr & ~MethodAttributes.MemberAccessMask;
+                       var s_no_visibility = sAttr & ~MethodAttributes.MemberAccessMask;
+                       return g_no_visibility | s_no_visibility | visibility;
+               }
+
+               void RenderPropertyType (XElement source, XElement target, ApiChange change)
+               {
+                       var srcType = source.GetTypeName ("ptype");
+                       var tgtType = target.GetTypeName ("ptype");
+
+                       if (srcType == tgtType) {
+                               change.Append (tgtType);
+                       } else {
+                               change.AppendModified (srcType, tgtType, true);
+                       }
+                       change.Append (" ");
+               }
+
+               void RenderAccessors (XElement srcGetter, XElement tgtGetter, XElement srcSetter, XElement tgtSetter, ApiChange change)
+               {
+                       // FIXME: this doesn't render changes in the accessor visibility (a protected setter can become public for instance).
+                       change.Append (" {");
+                       if (tgtGetter != null) {
+                               if (srcGetter != null) {
+                                       change.Append (" ").Append ("get;");
+                               } else {
+                                       change.Append (" ").AppendAdded ("get;");
+                               }
+                       } else if (srcGetter != null) {
+                               change.Append (" ").AppendRemoved ("get;");
+                       }
+
+                       if (tgtSetter != null) {
+                               if (srcSetter != null) {
+                                       change.Append (" ").Append ("set;");
+                               } else {
+                                       change.Append (" ").AppendAdded ("set;");
+                               }
+                       } else if (srcSetter != null) {
+                               change.Append (" ").AppendRemoved ("set;");
+                       }
+
+                       change.Append (" }");
+
+                       // Ignore added property setters if asked to
+                       if (srcSetter == null && tgtSetter != null && State.IgnoreAddedPropertySetters && !change.Breaking) {
+                               change.AnyChange = false;
+                               change.HasIgnoredChanges = true;
+                       }
+               }
+
+               void RenderIndexers (List<XElement> srcIndexers, List<XElement> tgtIndexers, ApiChange change)
+               {
+                       change.Append ("this [");
+                       for (int i = 0; i < srcIndexers.Count; i++) {
+                               var source = srcIndexers [i];
+                               var target = tgtIndexers [i];
+
+                               if (i > 0)
+                                       change.Append (", ");
+
+                               var srcType = source.GetTypeName ("type");
+                               var tgtType = target.GetTypeName ("type");
+                               if (srcType == tgtType) {
+                                       change.Append (tgtType);
+                               } else {
+                                       change.AppendModified (srcType, tgtType, true);
+                               }
+                               change.Append (" ");
+
+                               var srcName = source.GetAttribute ("name");
+                               var tgtName = target.GetAttribute ("name");
+                               if (srcName == tgtName) {
+                                       change.Append (tgtName);
+                               } else {
+                                       change.AppendModified (srcName, tgtName, true);
+                               }
+                       }
+                       change.Append ("]");
+               }
+
+               public override bool Equals (XElement source, XElement target, ApiChanges changes)
+               {
+                       if (base.Equals (source, target, changes))
+                               return true;
+
+                       XElement srcGetter, srcSetter;
+                       XElement tgtGetter, tgtSetter;
+                       GetAccessors (source, out srcGetter, out srcSetter);
+                       GetAccessors (target, out tgtGetter, out tgtSetter);
+
+                       List<XElement> srcIndexers = null;
+                       List<XElement> tgtIndexers = null;
+                       bool isIndexer = false;
+                       if (srcGetter != null) {
+                               srcIndexers = srcGetter.DescendantList ("parameters", "parameter");
+                               tgtIndexers = tgtGetter.DescendantList ("parameters", "parameter");
+                               isIndexer = srcIndexers != null && srcIndexers.Count > 0;
+                       }
+
+                       var change = new ApiChange ();
+                       change.Header = "Modified " + GroupName;
+                       RenderMethodAttributes (GetMethodAttributes (srcGetter, srcSetter), GetMethodAttributes (tgtGetter, tgtSetter), change);
+                       RenderPropertyType (source, target, change);
+                       if (isIndexer) {
+                               RenderIndexers (srcIndexers, tgtIndexers, change);
+                       } else {
+                               RenderName (source, target, change);
+                       }
+                       RenderGenericParameters (source, target, change);
+                       RenderAccessors (srcGetter, tgtGetter, srcSetter, tgtSetter, change);
+
+                       changes.Add (source, target, change);
+
+                       return false;
+               }
+
+               void GetProperties (XElement e, out bool @virtual, out bool @override, out bool @static, out bool getter, out bool setter, out bool family)
+               {
+                       @virtual = @override = @static = getter = setter = family = false;
+
+                       var methods = e.Element ("methods");
+                       if (methods != null) {
+                               foreach (var m in methods.Elements ("method")) {
+                                       @virtual |= m.IsTrue ("virtual");
+                                       @static |= m.IsTrue ("static");
+                                       var n = m.GetAttribute ("name");
+                                       getter |= n.StartsWith ("get_", StringComparison.Ordinal);
+                                       setter |= n.StartsWith ("set_", StringComparison.Ordinal);
+                                       var attribs = (MethodAttributes) Int32.Parse (m.GetAttribute ("attrib"));
+                                       family = ((attribs & MethodAttributes.Public) != MethodAttributes.Public);
+                                       @override |= (attribs & MethodAttributes.NewSlot) == 0;
+                               }
+                       }
+               }
+
+               public override string GetDescription (XElement e)
+               {
+                       string name = e.Attribute ("name").Value;
+                       string ptype = e.GetTypeName ("ptype");
+
+                       bool virt = false;
+                       bool over = false;
+                       bool stat = false;
+                       bool getter = false;
+                       bool setter = false;
+                       bool family = false;
+                       GetProperties (e, out virt, out over, out stat, out getter, out setter, out family);
+
+                       var sb = new StringBuilder ();
+
+                       sb.Append (family ? "protected " : "public ");
+                       if (virt && !State.IgnoreVirtualChanges)
+                               sb.Append (over ? "override " : "virtual ");
+                       else if (stat)
+                               sb.Append ("static ");
+                       sb.Append (ptype).Append (' ').Append (name).Append (" { ");
+                       if (getter)
+                               sb.Append ("get; ");
+                       if (setter)
+                               sb.Append ("set; ");
+                       sb.Append ("}");
+
+                       return sb.ToString ();
+               }
+       }
+}
\ No newline at end of file
diff --git a/mcs/tools/mono-api-html/mono-api-html.csproj b/mcs/tools/mono-api-html/mono-api-html.csproj
new file mode 100644 (file)
index 0000000..103d817
--- /dev/null
@@ -0,0 +1,57 @@
+<?xml version="1.0" encoding="utf-8"?>
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
+  <PropertyGroup>
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
+    <Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
+    <ProductVersion>8.0.30703</ProductVersion>
+    <SchemaVersion>2.0</SchemaVersion>
+    <ProjectGuid>{D25986E2-7A41-4966-A26D-5614BAC7B8A7}</ProjectGuid>
+    <OutputType>Exe</OutputType>
+    <RootNamespace>Xamarin.ApiDiff</RootNamespace>
+    <AssemblyName>mono-api-html</AssemblyName>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
+    <DebugSymbols>true</DebugSymbols>
+    <DebugType>full</DebugType>
+    <Optimize>false</Optimize>
+    <OutputPath>bin\Debug</OutputPath>
+    <DefineConstants>DEBUG;</DefineConstants>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+    <ConsolePause>false</ConsolePause>
+  </PropertyGroup>
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
+    <DebugType>full</DebugType>
+    <Optimize>true</Optimize>
+    <OutputPath>bin\Release</OutputPath>
+    <ErrorReport>prompt</ErrorReport>
+    <WarningLevel>4</WarningLevel>
+    <Externalconsole>true</Externalconsole>
+  </PropertyGroup>
+  <ItemGroup>
+    <Reference Include="System" />
+    <Reference Include="System.Xml.Linq" />
+    <Reference Include="System.Xml" />
+    <Reference Include="System.Core" />
+  </ItemGroup>
+  <ItemGroup>
+    <Compile Include="Helpers.cs" />
+    <Compile Include="InterfaceComparer.cs" />
+    <Compile Include="NamespaceComparer.cs" />
+    <Compile Include="MemberComparer.cs" />
+    <Compile Include="FieldComparer.cs" />
+    <Compile Include="PropertyComparer.cs" />
+    <Compile Include="EventComparer.cs" />
+    <Compile Include="MethodComparer.cs" />
+    <Compile Include="ConstructorComparer.cs" />
+    <Compile Include="Comparer.cs" />
+    <Compile Include="AssemblyComparer.cs" />
+    <Compile Include="ClassComparer.cs" />
+    <Compile Include="ApiDiff.cs" />
+    <Compile Include="..\..\class\Mono.Options\Mono.Options\Options.cs">
+      <Link>Options.cs</Link>
+    </Compile>
+    <Compile Include="ApiChange.cs" />
+  </ItemGroup>
+  <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />
+</Project>
diff --git a/mcs/tools/mono-api-html/mono-api-html.exe.sources b/mcs/tools/mono-api-html/mono-api-html.exe.sources
new file mode 100644 (file)
index 0000000..69a2679
--- /dev/null
@@ -0,0 +1,15 @@
+ApiChange.cs
+ApiDiff.cs
+AssemblyComparer.cs
+ClassComparer.cs
+Comparer.cs
+ConstructorComparer.cs
+EventComparer.cs
+FieldComparer.cs
+Helpers.cs
+InterfaceComparer.cs
+MemberComparer.cs
+MethodComparer.cs
+NamespaceComparer.cs
+PropertyComparer.cs
+../../class/Mono.Options/Mono.Options/Options.cs
index 36d7feb5946ff49b8c0053ea68c68ac987b0b1aa..fe3b52f8d213ba8d713445c79878e7347473d6aa 100644 (file)
@@ -2,11 +2,8 @@ thisdir = tools/mono-configuration-crypto/cli
 SUBDIRS = 
 include ../../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:Mono.Security.dll \
-                 -r:System.Security.dll \
-                 -r:System.Configuration.dll \
-                 -r:System.dll \
-                 -r:$(topdir)/class/lib/$(PROFILE)/Mono.Configuration.Crypto.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = Mono.Security System.Security System.Configuration System Mono.Configuration.Crypto
 
 PROGRAM = mono-configuration-crypto.exe
 PROGRAM_INSTALL_DIR = $(mono_libdir)/mono/mono-configuration-crypto/$(FRAMEWORK_VERSION)
index 06351749f74360d7b70e454012f6367ba069a49f..d06b52ae235c72d16a707948b4af176374ccfb57 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mono-configuration-crypto/lib
 SUBDIRS =
 include ../../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:Mono.Security.dll -r:System.Security.dll -r:System.Configuration.dll -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System Mono.Security System.Security System.Configuration System.Xml
 LIBRARY = Mono.Configuration.Crypto.dll
 LIBRARY_INSTALL_DIR = $(mono_libdir)/mono/mono-configuration-crypto/$(FRAMEWORK_VERSION)
 
index 7e8331eb46acbb1864fa0614bd835a1b7656c49b..84286e7f95fffbf75b4559235ea776e10005d7c5 100644 (file)
@@ -4,9 +4,12 @@ include ../../build/rules.make
 
 PROGRAM = mono-service.exe
 
+PROGRAM_SNK = ../../class/mono.snk
+
 include ../../build/executable.make
 
-LOCAL_MCS_FLAGS = -r:System.ServiceProcess.dll -r:Mono.Posix.dll -r:System.dll -unsafe
+LOCAL_MCS_FLAGS = -unsafe -publicsign
+LIB_REFS = System.ServiceProcess Mono.Posix System
 
 # Copied from library.make
 
index e4e4b557eb431584db275f77fa28bba95f6f1a34..2bfc65599d9abfef1c2b5cf6509dd0b420b0ca71 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mono-shlib-cop
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:Mono.Posix.dll -r:System.dll -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = Mono.Posix System System.Xml
 
 PROGRAM = mono-shlib-cop.exe
 
index 2fc8018c7b492d35bf26e46193ca5acadfc1d5b7..01a7ceb97d9d7b328ad92007b57df1ac93bd3b80 100644 (file)
@@ -2,90 +2,152 @@ using System;
 using System.IO;
 using System.Linq;
 using System.Text;
-using System.Reflection;
-using System.Diagnostics;
 using System.Collections.Generic;
 using Mono.Cecil;
-using Mono.CompilerServices.SymbolWriter;
+using Mono.Cecil.Cil;
+using Mono.Collections.Generic;
 
 namespace Symbolicate
 {
-       struct Location {
-               public string FileName;
-               public int Line;
-       }
-
        class LocationProvider {
                class AssemblyLocationProvider {
-                       Assembly assembly;
-                       MonoSymbolFile symbolFile;
+                       AssemblyDefinition assembly;
                        string seqPointDataPath;
 
-                       public AssemblyLocationProvider (Assembly assembly, MonoSymbolFile symbolFile, string seqPointDataPath)
+                       public AssemblyLocationProvider (AssemblyDefinition assembly, string seqPointDataPath)
                        {
                                this.assembly = assembly;
-                               this.symbolFile = symbolFile;
                                this.seqPointDataPath = seqPointDataPath;
                        }
 
-                       public bool TryGetLocation (string methodStr, string typeFullName, int offset, bool isOffsetIL, uint methodIndex, out Location location)
+                       public SequencePoint TryGetLocation (string typeFullName, string methodSignature, int offset, bool isOffsetIL, uint methodIndex)
                        {
-                               location = default (Location);
-                               if (symbolFile == null)
-                                       return false;
-
-                               var type = assembly.GetTypes().FirstOrDefault (t => t.FullName == typeFullName);
-                               if (type == null)
-                                       return false;
+                               if (!assembly.MainModule.HasSymbols)
+                                       return null;
+
+                               TypeDefinition type = null;
+                               var nested = typeFullName.Split ('+');
+                               var types = assembly.MainModule.Types;
+                               foreach (var ntype in nested) {
+                                       type = types.FirstOrDefault (t => t.Name == ntype);
+                                       if (type == null)
+                                               return null;
+
+                                       types = type.NestedTypes;
+                               }
 
-                               var bindingflags = BindingFlags.Instance | BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic;
-                               var method = type.GetMethods(bindingflags).FirstOrDefault (m => GetMethodFullName (m) == methodStr);
+                               var parensStart = methodSignature.IndexOf ('(');
+                               var methodName = methodSignature.Substring (0, parensStart).TrimEnd ();
+                               var methodParameters = methodSignature.Substring (parensStart);
+                               var method = type.Methods.FirstOrDefault (m => CompareName (m, methodName) && CompareParameters (m.Parameters, methodParameters));
                                if (method == null)
-                                       return false;
+                                       return null;
 
-                               int ilOffset = (isOffsetIL)? offset : GetILOffsetFromFile (method.MetadataToken, methodIndex, offset);
+                               int ilOffset = isOffsetIL ? offset : GetILOffsetFromFile (method.MetadataToken.ToInt32 (), methodIndex, offset);
                                if (ilOffset < 0)
-                                       return false;
+                                       return null;
+
+                               SequencePoint sp = null;
+                               foreach (var instr in method.Body.Instructions) {
+                                       if (instr.SequencePoint != null)
+                                               sp = instr.SequencePoint;
+                                       
+                                       if (instr.Offset >= ilOffset) {
+                                               return sp;
+                                       }
+                               }
 
-                               var methodSymbol = symbolFile.Methods [(method.MetadataToken & 0x00ffffff) - 1];
+                               return null;
+                       }
 
-                               var lineNumbers = methodSymbol.GetLineNumberTable ().LineNumbers;
-                               var lineNumber = lineNumbers.FirstOrDefault (l => l.Offset >= ilOffset) ?? lineNumbers.Last ();
+                       SeqPointInfo seqPointInfo;
+                       private int GetILOffsetFromFile (int methodToken, uint methodIndex, int nativeOffset)
+                       {
+                               if (seqPointInfo == null)
+                                       seqPointInfo = SeqPointInfo.Read (seqPointDataPath);
 
-                               location.FileName = symbolFile.Sources [lineNumber.File-1].FileName;
-                               location.Line = lineNumber.Row;
-                               return true;
+                               return seqPointInfo.GetILOffset (methodToken, methodIndex, nativeOffset);
                        }
 
-                       static MethodInfo methodGetIL;
-                       private int GetILOffsetFromFile (int methodToken, uint methodIndex, int nativeOffset)
+                       static bool CompareName (MethodDefinition candidate, string expected)
                        {
-                               if (string.IsNullOrEmpty (seqPointDataPath))
-                                       return -1;
+                               if (candidate.Name == expected)
+                                       return true;
+
+                               if (!candidate.HasGenericParameters)
+                                       return false;
+                               
+                               var genStart = expected.IndexOf ('[');
+                               if (genStart < 0)
+                                       return false;
 
-                               if (methodGetIL == null)
-                                       methodGetIL = typeof (StackFrame).GetMethod ("GetILOffsetFromFile", BindingFlags.NonPublic | BindingFlags.Static);
+                               if (candidate.Name != expected.Substring (0, genStart))
+                                       return false;
 
-                               if (methodGetIL == null)
-                                       throw new Exception ("System.Diagnostics.StackFrame.GetILOffsetFromFile could not be found, make sure you have an updated mono installed.");
+                               int arity = 1;
+                               for (int pos = genStart; pos < expected.Length; ++pos) {
+                                       if (expected [pos] == ',')
+                                               ++arity;
+                               }
 
-                               return (int) methodGetIL.Invoke (null, new object[] {seqPointDataPath, methodToken, methodIndex, nativeOffset});
+                               return candidate.GenericParameters.Count == arity;
                        }
 
-                       static MethodInfo methodGetMethodFullName;
-                       private string GetMethodFullName (MethodBase m)
+                       static bool CompareParameters (Collection<ParameterDefinition> candidate, string expected)
                        {
+                               var builder = new StringBuilder ();
+                               builder.Append ("(");
 
-                               if (methodGetMethodFullName == null)
-                                       methodGetMethodFullName = typeof (StackTrace).GetMethod ("GetFullNameForStackTrace", BindingFlags.NonPublic | BindingFlags.Static);
+                               for (int i = 0; i < candidate.Count; i++) {
+                                       var parameter = candidate [i];
+                                       if (i > 0)
+                                               builder.Append (", ");
 
-                               if (methodGetMethodFullName == null)
-                                       throw new Exception ("System.Exception.GetFullNameForStackTrace could not be found, make sure you have an updated mono installed.");
+                                       if (parameter.ParameterType.IsSentinel)
+                                               builder.Append ("...,");
+
+                                       var pt = parameter.ParameterType;
+                                       if (!string.IsNullOrEmpty (pt.Namespace)) {
+                                               builder.Append (pt.Namespace);
+                                               builder.Append (".");
+                                       }
+
+                                       FormatElementType (pt, builder);
+
+                                       builder.Append (" ");
+                                       builder.Append (parameter.Name);
+                               }
 
-                               StringBuilder sb = new StringBuilder ();
-                               methodGetMethodFullName.Invoke (null, new object[] {sb, m});
+                               builder.Append (")");
 
-                               return sb.ToString ();
+                               return builder.ToString () == expected;
+                       }
+
+                       static void FormatElementType (TypeReference tr, StringBuilder builder)
+                       {
+                               var ts = tr as TypeSpecification;
+                               if (ts != null) {
+                                       if (ts.IsByReference) {
+                                               FormatElementType (ts.ElementType, builder);
+                                               builder.Append ("&");
+                                               return;
+                                       }
+
+                                       var array = ts as ArrayType;
+                                       if (array != null) {
+                                               FormatElementType (ts.ElementType, builder);
+                                               builder.Append ("[");
+
+                                               for (int ii = 0; ii < array.Rank - 1; ++ii) {
+                                                       builder.Append (",");
+                                               }
+
+                                               builder.Append ("]");
+                                               return;
+                                       }
+                               }
+
+                               builder.Append (tr.Name);
                        }
                }
 
@@ -106,24 +168,19 @@ namespace Symbolicate
                        if (!File.Exists (assemblyPath))
                                throw new ArgumentException ("assemblyPath does not exist: "+ assemblyPath);
 
-                       var assembly = Assembly.LoadFrom (assemblyPath);
-                       MonoSymbolFile symbolFile = null;
-
-                       var symbolPath = assemblyPath + ".mdb";
-                       if (!File.Exists (symbolPath))
-                               Debug.WriteLine (".mdb file was not found for " + assemblyPath);
-                       else
-                               symbolFile = MonoSymbolFile.ReadSymbolFile (assemblyPath + ".mdb");
+                       var readerParameters = new ReaderParameters { ReadSymbols = true };
+                       var assembly = AssemblyDefinition.ReadAssembly (assemblyPath, readerParameters);
 
                        var seqPointDataPath = assemblyPath + ".msym";
                        if (!File.Exists (seqPointDataPath))
                                seqPointDataPath = null;
 
-                       assemblies.Add (assemblyPath, new AssemblyLocationProvider (assembly, symbolFile, seqPointDataPath));
+                       assemblies.Add (assemblyPath, new AssemblyLocationProvider (assembly, seqPointDataPath));
 
+                       // TODO: Should use AssemblyName with .net unification rules
                        directories.Add (Path.GetDirectoryName (assemblyPath));
 
-                       foreach (var assemblyRef in assembly.GetReferencedAssemblies ()) {
+                       foreach (var assemblyRef in assembly.MainModule.AssemblyReferences) {
                                string refPath = null;
                                foreach (var dir in directories) {
                                        refPath = Path.Combine (dir, assemblyRef.Name);
@@ -153,15 +210,15 @@ namespace Symbolicate
                        directories.Add (directory);
                }
 
-               public bool TryGetLocation (string method, string typeFullName, int offset, bool isOffsetIL, uint methodIndex, out Location location)
+               public SequencePoint TryGetLocation (string typeFullName, string methodSignature, int offset, bool isOffsetIL, uint methodIndex)
                {
-                       location = default (Location);
                        foreach (var assembly in assemblies.Values) {
-                               if (assembly.TryGetLocation (method, typeFullName, offset, isOffsetIL, methodIndex, out location))
-                                       return true;
+                               var loc = assembly.TryGetLocation (typeFullName, methodSignature, offset, isOffsetIL, methodIndex);
+                               if (loc != null)
+                                       return loc;
                        }
 
-                       return false;
+                       return null;
                }
        }
 }
index 35cdfd88a39e21ee4d503c0316bbc2c31577d1a7..3c30921a61e18e2b3d239d3356eefda34260099f 100644 (file)
@@ -5,11 +5,9 @@ include ../../build/rules.make
 PROGRAM = mono-symbolicate.exe
 
 LOCAL_MCS_FLAGS = \
-       /r:Mono.Cecil.dll       \
-       /r:Mono.CompilerServices.SymbolWriter.dll \
-       /r:System.Xml.dll \
-       /r:System.Core.dll \
-       /r:System.dll
+       /D:NO_AUTHENTICODE
+
+LIB_REFS = Mono.Cecil Mono.Cecil.Mdb System.Xml System.Core System
 
 include ../../build/executable.make
 
@@ -36,10 +34,10 @@ CHECK_DIFF = @\
                exit 1; \
        fi
 
-BUILD_TEST_EXE = @\
+BUILD_TEST_EXE = \
        rm -rf $(OUT_DIR); \
        mkdir -p $(OUT_DIR); \
-       $(MCS) -debug $(TEST_CS) -out:$(TEST_EXE)
+       $(CSCOMPILE) $(TEST_CS) -out:$(TEST_EXE)
 
 check: test-local
 
@@ -47,13 +45,13 @@ AOT_SUPPORTED = $(shell $(MONO) --aot 2>&1 | grep -q "AOT compilation is not sup
 
 test-local: all
        $(BUILD_TEST_EXE)
-       @echo "Checking $(PROGRAM) without AOT"
+       @echo "Checking $(TEST_EXE) without AOT"
        $(CHECK_DIFF)
 ifeq ($(AOT_SUPPORTED), 1)
-       @echo "Checking $(PROGRAM) with AOT"
+       @echo "Checking $(TEST_EXE) with AOT"
        @MONO_DEBUG=gen-compact-seq-points $(MONO) --aot $(TEST_EXE) > /dev/null
        $(CHECK_DIFF)
-       @echo "Checking $(PROGRAM) with AOT (using .msym)"
+       @echo "Checking $(TEST_EXE) with AOT (using .msym)"
        $(BUILD_TEST_EXE)
        @MONO_DEBUG=gen-compact-seq-points $(MONO) --aot=gen-seq-points-file $(TEST_EXE) > /dev/null
        $(CHECK_DIFF)
diff --git a/mcs/tools/mono-symbolicate/SeqPointInfo.cs b/mcs/tools/mono-symbolicate/SeqPointInfo.cs
new file mode 100644 (file)
index 0000000..606e4fb
--- /dev/null
@@ -0,0 +1,156 @@
+using System;
+using System.IO;
+using System.Collections.Generic;
+
+namespace Symbolicate
+{
+       static class BinaryReaderExtensions
+       {
+               public static int ReadVariableInt (this BinaryReader reader)
+               {
+                       int val = 0;
+                       for (var i = 0; i < 4; i++) {
+                               var b = reader.ReadByte ();
+                               val |= (b & 0x7f) << (7 * i);
+                               if ((b & 0x80) == 0)
+                                       return val;
+                       }
+
+                       throw new Exception ("Invalid variable int");
+               }
+
+               public static int ReadVariableZigZagInt (this BinaryReader reader)
+               {
+                       int enc = ReadVariableInt (reader);
+                       int val = enc >> 1;
+                       return ((enc & 1) == 0)? val : -val;
+               }
+       }
+
+       class SeqPointInfo
+       {
+               class MethodData
+               {
+                       List<SeqPoint> seqPoints;
+
+                       public static MethodData Read (BinaryReader reader)
+                       {
+                               var hasDebugData = reader.ReadVariableInt () != 0;
+                               var dataSize = reader.ReadVariableInt ();
+                               var dataEnd = reader.BaseStream.Position + dataSize;
+
+                               var seqPoints = new List<SeqPoint> ();
+                               SeqPoint prev = null;
+                               while (reader.BaseStream.Position < dataEnd) {
+                                       var seqPoint = SeqPoint.Read (reader, prev, hasDebugData);
+                                       seqPoints.Add (seqPoint);
+                                       prev = seqPoint;
+                               }
+
+                               if (reader.BaseStream.Position != dataEnd)
+                                       throw new Exception ("Read more seq point than expected.");
+
+                               return new MethodData () { seqPoints = seqPoints };
+                       }
+
+                       public bool TryGetILOffset (int nativeOffset, out int ilOffset)
+                       {
+                               ilOffset = 0;
+                               SeqPoint prev = null;
+                               foreach (var seqPoint in seqPoints) {
+                                       if (seqPoint.NativeOffset > nativeOffset)
+                                               break;
+                                       prev = seqPoint;
+                               }
+
+                               if (prev == null)
+                                       return false;
+
+                               ilOffset = prev.ILOffset;
+                               return true;
+                       }
+               }
+
+               class SeqPoint
+               {
+                       public readonly int ILOffset;
+                       public readonly int NativeOffset;
+
+                       public SeqPoint (int ilOffset, int nativeOffset)
+                       {
+                               ILOffset = ilOffset;
+                               NativeOffset = nativeOffset;
+                       }
+
+                       public static SeqPoint Read (BinaryReader reader, SeqPoint prev, bool hasDebug)
+                       {
+                               var ilOffset = reader.ReadVariableZigZagInt ();
+                               var nativeOffset = reader.ReadVariableZigZagInt ();
+
+                               // Respect delta encoding
+                               if (prev != null) {
+                                       ilOffset += prev.ILOffset;
+                                       nativeOffset += prev.NativeOffset;
+                               }
+
+                               //Read everything to ensure the buffer position is at the end of the seq point data.
+                               if (hasDebug) {
+                                       reader.ReadVariableInt (); // flags
+
+                                       var next_length = reader.ReadVariableInt ();
+                                       for (var i = 0; i < next_length; ++i)
+                                               reader.ReadVariableInt ();
+                               }
+
+                               return new SeqPoint (ilOffset, nativeOffset);
+                       }
+               };
+
+               Dictionary<Tuple<int,int>, MethodData> dataByIds;
+               Dictionary<int, MethodData> dataByTokens;
+
+               public static SeqPointInfo Read (string path)
+               {
+                       using (var reader = new BinaryReader (File.Open (path, FileMode.Open)))
+                       {
+                               var dataByIds = new Dictionary<Tuple<int,int>, MethodData> ();
+                               var dataByTokens = new Dictionary<int, MethodData> ();
+
+                               var methodCount = reader.ReadVariableInt ();
+
+                               for (var i = 0; i < methodCount; ++i) {
+                                       var methodToken = reader.ReadVariableInt ();
+                                       var methodIndex = reader.ReadVariableInt ();
+                                       var methodId = new Tuple<int, int> (methodToken, methodIndex);
+
+                                       var methodData = MethodData.Read (reader);
+
+                                       dataByIds.Add (methodId, methodData);
+                                       if (!dataByTokens.ContainsKey (methodToken))
+                                               dataByTokens.Add (methodToken, methodData);
+                               }
+
+                               return new SeqPointInfo { dataByIds  = dataByIds, dataByTokens = dataByTokens };
+                       }
+               }
+
+               public int GetILOffset (int methodToken, uint methodIndex, int nativeOffset)
+               {
+                       MethodData methodData;
+                       if (methodIndex == 0xffffff) {
+                          if (!dataByTokens.TryGetValue (methodToken, out methodData))
+                                       throw new Exception (string.Format ("Could not find data for method token {0:X}", methodToken));
+                       } else {
+                               var methodId = new Tuple<int, int> (methodToken, (int)methodIndex);
+                               if (!dataByIds.TryGetValue (methodId, out methodData))
+                                       throw new Exception (string.Format ("Could not find data for method token {0:X} with index {1:X}", methodToken, methodIndex));
+                       }
+
+                       int ilOffset;
+                       if (!methodData.TryGetILOffset (nativeOffset, out ilOffset))
+                               throw new Exception ("Could not retrieve IL offset");
+
+                       return ilOffset;
+               }
+       }
+}
index a426d61200eaed9a2c3e8664903605e3f015d807..a3cd72acd0ef271381ede360b4d50799ca61c8fb 100644 (file)
@@ -11,22 +11,22 @@ Stacktrace:
   at StackTraceDumper.Catch (System.Action action) in StackTraceDumper.cs:54 
 
 System.Exception: Stacktrace with 3 frames
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:78 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:78 
   at StackTraceDumper.<Main>m__1 () in StackTraceDumper.cs:18 
   at StackTraceDumper.Catch (System.Action action) in StackTraceDumper.cs:54 
 Stacktrace:
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:78 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:78 
   at StackTraceDumper.<Main>m__1 () in StackTraceDumper.cs:18 
   at StackTraceDumper.Catch (System.Action action) in StackTraceDumper.cs:54 
 
 System.Exception: Stacktrace with 4 frames
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:78 
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:76 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:78 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:76 
   at StackTraceDumper.<Main>m__2 () in StackTraceDumper.cs:20 
   at StackTraceDumper.Catch (System.Action action) in StackTraceDumper.cs:54 
 Stacktrace:
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:78 
-  at StackTraceDumper.ThrowException (System.String message, Int32 i) in StackTraceDumper.cs:76 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:78 
+  at StackTraceDumper.ThrowException (System.String message, System.Int32 i) in StackTraceDumper.cs:76 
   at StackTraceDumper.<Main>m__2 () in StackTraceDumper.cs:20 
   at StackTraceDumper.Catch (System.Action action) in StackTraceDumper.cs:54 
 
index 968d028d0e95a50ac0f9a060963714a545036a7b..5c4437ba56945b09750b3dbe362a8b1441ccd1bc 100644 (file)
@@ -1,2 +1,3 @@
 symbolicate.cs
-LocationProvider.cs
\ No newline at end of file
+LocationProvider.cs
+SeqPointInfo.cs
diff --git a/mcs/tools/mono-symbolicate/monosymbolicate.csproj b/mcs/tools/mono-symbolicate/monosymbolicate.csproj
new file mode 100644 (file)
index 0000000..023e181
--- /dev/null
@@ -0,0 +1,50 @@
+<?xml version="1.0" encoding="utf-8"?>\r
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
+  <PropertyGroup>\r
+    <Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>\r
+    <Platform Condition=" '$(Platform)' == '' ">x86</Platform>\r
+    <ProjectGuid>{804E854F-E8F5-4E2B-807A-4FAF4BE99C03}</ProjectGuid>\r
+    <OutputType>Exe</OutputType>\r
+    <RootNamespace>monosymbolicate</RootNamespace>\r
+    <AssemblyName>monosymbolicate</AssemblyName>\r
+    <TargetFrameworkVersion>v4.5</TargetFrameworkVersion>\r
+    <ProductVersion>8.0.30703</ProductVersion>\r
+    <SchemaVersion>2.0</SchemaVersion>\r
+  </PropertyGroup>\r
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|x86' ">\r
+    <DebugSymbols>true</DebugSymbols>\r
+    <DebugType>full</DebugType>\r
+    <Optimize>false</Optimize>\r
+    <OutputPath>bin\Debug</OutputPath>\r
+    <DefineConstants>DEBUG;NO_AUTHENTICODE</DefineConstants>\r
+    <ErrorReport>prompt</ErrorReport>\r
+    <WarningLevel>4</WarningLevel>\r
+    <ExternalConsole>false</ExternalConsole>\r
+    <PlatformTarget>x86</PlatformTarget>\r
+    <Commandlineparameters></Commandlineparameters>\r
+    <ConsolePause>false</ConsolePause>\r
+  </PropertyGroup>\r
+  <PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|x86' ">\r
+    <Optimize>true</Optimize>\r
+    <OutputPath>bin\Release</OutputPath>\r
+    <ErrorReport>prompt</ErrorReport>\r
+    <WarningLevel>4</WarningLevel>\r
+    <ExternalConsole>true</ExternalConsole>\r
+    <PlatformTarget>x86</PlatformTarget>\r
+  </PropertyGroup>\r
+  <ItemGroup>\r
+    <Reference Include="System" />\r
+    <Reference Include="Mono.Cecil">\r
+      <HintPath>..\..\class\lib\net_4_x\Mono.Cecil.dll</HintPath>\r
+    </Reference>\r
+    <Reference Include="Mono.Cecil.Mdb">\r
+      <HintPath>..\..\class\lib\net_4_x\Mono.Cecil.Mdb.dll</HintPath>\r
+    </Reference>\r
+  </ItemGroup>\r
+  <ItemGroup>\r
+    <Compile Include="LocationProvider.cs" />\r
+    <Compile Include="SeqPointInfo.cs" />\r
+    <Compile Include="symbolicate.cs" />\r
+  </ItemGroup>\r
+  <Import Project="$(MSBuildBinPath)\Microsoft.CSharp.targets" />\r
+</Project>
\ No newline at end of file
index 4dd23e3d1bd16fea494ae918bcfd269b2532bc09..cb7aa9a46cd38ffc30d16ba877d0c7a10d20f3c7 100644 (file)
@@ -42,9 +42,9 @@ namespace Symbolicate
                        if (!match.Success)
                                return line;
 
-                       string typeFullName;
+                       string typeFullName, methodSignature;
                        var methodStr = match.Groups ["Method"].Value.Trim ();
-                       if (!TryParseMethodType (methodStr, out typeFullName))
+                       if (!ExtractSignatures (methodStr, out typeFullName, out methodSignature))
                                return line;
 
                        var isOffsetIL = !string.IsNullOrEmpty (match.Groups ["IL"].Value);
@@ -55,34 +55,37 @@ namespace Symbolicate
                        if (!string.IsNullOrEmpty (match.Groups ["MethodIndex"].Value))
                                methodIndex = uint.Parse (match.Groups ["MethodIndex"].Value, CultureInfo.InvariantCulture);
 
-                       Location location;
-                       if (!locProvider.TryGetLocation (methodStr, typeFullName, offset, isOffsetIL, methodIndex, out location))
+                       var loc = locProvider.TryGetLocation (typeFullName, methodSignature, offset, isOffsetIL, methodIndex);
+                       if (loc == null)
                                return line;
 
-                       return line.Replace ("<filename unknown>:0", string.Format ("{0}:{1}", location.FileName, location.Line));
+                       return line.Replace ("<filename unknown>:0", string.Format ("{0}:{1}", loc.Document.Url, loc.StartLine));
                }
 
-               static bool TryParseMethodType (string str, out string typeFullName)
+               static bool ExtractSignatures (string str, out string typeFullName, out string methodSignature)
                {
-                       typeFullName = null;
-
-                       var methodNameEnd = str.IndexOf ("(");
-                       if (methodNameEnd == -1)
+                       var methodNameEnd = str.IndexOf ('(');
+                       if (methodNameEnd == -1) {
+                               typeFullName = methodSignature = null;
                                return false;
+                       }
 
-                       // Remove parameters
-                       str = str.Substring (0, methodNameEnd);
-
-                       // Remove generic parameters
-                       str = Regex.Replace (str, @"\[[^\[\]]*\]", "");
-
-                       var typeNameEnd = str.LastIndexOf (".");
-                       if (methodNameEnd == -1 || typeNameEnd == -1)
+                       var typeNameEnd = str.LastIndexOf ('.', methodNameEnd);
+                       if (typeNameEnd == -1) {
+                               typeFullName = methodSignature = null;
                                return false;
+                       }
+
+                       // Adjustment for Type..ctor ()
+                       if (typeNameEnd > 0 && str [typeNameEnd - 1] == '.') {
+                               --typeNameEnd;
+                       }
 
-                       // Remove method name
                        typeFullName = str.Substring (0, typeNameEnd);
+                       // Remove generic parameters
+                       typeFullName = Regex.Replace (typeFullName, @"\[[^\[\]]*\]", "");
 
+                       methodSignature = str.Substring (typeNameEnd + 1);
                        return true;
                }
        }
index fc39f8298abdbf07eab940cdece113ab7c772e1e..7439a2eb9dd8ee3ce2314e11386db963ed15ee44 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mono-xmltool
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:Commons.Xml.Relaxng.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml Commons.Xml.Relaxng
 PROGRAM = mono-xmltool.exe
 
 include ../../build/executable.make
index 85a08599fa7d107700ba39bbac25c04e7b8baa75..d9e77ac82512e62478431fa12d1092bb544bf101 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/mono-xsd
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:System.Data.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml System.Data System
 PROGRAM = xsd.exe
 
 include ../../build/executable.make
index 280122793695abea4a0cd10aafaa9e5633736d35..4e84d9916fa15b756445b5148fe51d1faa292c17 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../build/rules.make
 
 PROGRAM = monop.exe
-LOCAL_MCS_FLAGS += -d:NO_AUTHENTICODE,STATIC,NO_SYMBOL_WRITER -r:System.dll
+LOCAL_MCS_FLAGS += -d:NO_AUTHENTICODE,STATIC,NO_SYMBOL_WRITER
+LIB_REFS = System
 
 CLEAN_FILES = monop.exe monop2.exe *.mdb
 
index 61339b1a5cc54c0208bfdce507a971cbec418648..6e78792b5868ab5d47e7e593029a76e477b4c81a 100644 (file)
@@ -3,8 +3,8 @@ SUBDIRS =
 include ../../build/rules.make
 NO_TESTS = yes
 
-BUILD_FRAMEWORK = Microsoft.Build.Framework.dll
-BUILD_NEW_ENGINE = Microsoft.Build.dll
+BUILD_FRAMEWORK = Microsoft.Build.Framework
+BUILD_NEW_ENGINE = Microsoft.Build
 INSTALL_FRAMEWORK_VERSION = $(FRAMEWORK_VERSION)
 
 include ../xbuild/xbuild.make
@@ -16,13 +16,12 @@ else
 ifeq (4, $(FRAMEWORK_VERSION_MAJOR))
 NAME_SUFFIX = .v4.0
 ASSEMBLY_VERSION = 4.0.0.0
-BUILD_FRAMEWORK := $(topdir)/class/lib/$(PROFILE)/$(BUILD_FRAMEWORK)
-BUILD_NEW_ENGINE := $(topdir)/class/lib/$(PROFILE)/$(BUILD_NEW_ENGINE)
 INSTALL_FRAMEWORK_VERSION = 4.0
 endif
 endif
 
-LOCAL_MCS_FLAGS = -r:$(BUILD_FRAMEWORK) -r:$(BUILD_NEW_ENGINE)
+LOCAL_MCS_FLAGS =
+LIB_REFS = $(BUILD_FRAMEWORK) $(BUILD_NEW_ENGINE)
 PROGRAM = msbuild.exe
 
 include ../../build/executable.make
index 9dd062fe9c17d64b740cf05c7292407ce4e865c1..1d448c2915a429c91b9c5e1ee0fff76424ec6f93 100644 (file)
@@ -5,7 +5,8 @@ include ../../../build/rules.make
 LIBRARY = nunitlite.dll
 LIBRARY_SNK = ../../../../external/nunit-lite/NUnitLite-1.0.0/src/framework/nunit.snk
 
-LOCAL_MCS_FLAGS= /target:library /define:"__MOBILE__;TRACE;DEBUG;NET_4_0;CLR_4_0,NUNITLITE" /nostdlib -r:System.dll -r:System.Xml.dll -r:System.Core.dll -r:mscorlib.dll /warn:4 /noconfig /debug:full /debug+ /keyfile:$(LIBRARY_SNK) /optimize
+LOCAL_MCS_FLAGS= /target:library /define:"__MOBILE__;TRACE;DEBUG;NET_4_0;CLR_4_0,NUNITLITE" /warn:4 /keyfile:$(LIBRARY_SNK)
+LIB_REFS = System System.Xml System.Core
 
 NO_TEST = yes
 
index 920f74d29a5941b0702fda299a7ef8fa81c6f63c..c3697e420fce5135bb9f1e0e66f3dde69ec50913 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../../build/rules.make
 
 PROGRAM = nunit-lite-console.exe
-LOCAL_MCS_FLAGS = /r:nunitlite.dll 
+LIB_REFS = nunitlite
+LOCAL_MCS_FLAGS =
 
 include ../../../build/executable.make
 
index 057ddabea6985815875497e7634b628b921ead29..3d3f647bc3c54b77ac49c284fef7d49601300748 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 NO_INSTALL = 1
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml
 
 EXTRA_DISTFILES = \
        Media/*.png             \
index 8de09cc43e9be603deef79feefa7a3821c0aefc3..0d2f377310c452dd2762799fa4a11315c6295f79 100644 (file)
@@ -4,10 +4,8 @@ include ../../build/rules.make
 
 PROGRAM = pdb2mdb.exe
 
-LOCAL_MCS_FLAGS = \
-       /r:Mono.Cecil.dll       \
-       /r:Mono.CompilerServices.SymbolWriter.dll \
-       /r:System.Core.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = Mono.Cecil Mono.CompilerServices.SymbolWriter System.Core
 
 
 EXTRA_DISTFILES = LICENSE
index 117f99231d7289d325329229c49bf7e458fe0ed6..2ccbf5869c73ee3b6fe5b67a5d0c46bca88d76bb 100644 (file)
@@ -6,7 +6,7 @@ PROGRAM = resgen.exe
 
 CLEAN_FILES = resgen.exe
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Xml.dll -r:System.Core.dll
+LIB_REFS = System System.Xml System.Core
 
 INSTALL_PROFILE := $(filter $(DEFAULT_PROFILE), $(PROFILE))
 ifndef INSTALL_PROFILE
index d75599dcee58228921d6ceb6e2e66d4f2a90114c..e4bfbb4d315122fddfa2005af3bfcc6458b5a0d5 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 DIST_ONLY_SUBDIRS = certview
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = /lib:$(topdir)/class/lib/$(PROFILE) -r:Mono.Security.dll -r:System.dll
+LOCAL_MCS_FLAGS = 
+LIB_REFS = Mono.Security System
 
 SECURITY_PROGRAMS = secutil.exe cert2spc.exe sn.exe makecert.exe chktrust.exe crlupdate.exe \
        signcode.exe setreg.exe certmgr.exe caspol.exe permview.exe mozroots.exe cert-sync.exe
@@ -58,10 +59,10 @@ clean-local:
 dist-local: dist-default
 
 sn.exe $(topdir)/class/lib/$(PROFILE)/sn.exe: $(SN_SOURCES)
-       $(CSCOMPILE) /out:$@ $(SN_SOURCES)
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/Mono.Security.dll /out:$@ $(SN_SOURCES)
 
 permview.exe: permview.cs
-       $(CSCOMPILE) $^ $(HELPER_SOURCES) -r:Mono.Cecil.dll
+       $(CSCOMPILE) $^ $(HELPER_SOURCES) -r:$(topdir)/class/lib/$(PROFILE)/Mono.Cecil.dll
 
 %.exe: %.cs $(HELPER_SOURCES)
-       $(CSCOMPILE) $^
+       $(CSCOMPILE) -r:$(topdir)/class/lib/$(PROFILE)/Mono.Security.dll -r:$(topdir)/class/lib/$(PROFILE)/System.dll $^
index 377d396f01544b966efe696ca173a29e879d9f05..aaa92049f4ba4c34224be91fa86eb12b9d0ced1d 100644 (file)
@@ -3,7 +3,8 @@ SUBDIRS =
 include ../../../build/rules.make
 
 RESGEN = resgen
-LOCAL_MCS_FLAGS = /lib:$(topdir)/class/lib /r:Mono.Security.dll /r:System.Xml.dll /win32icon:mono.ico
+LIB_REFS = Mono.Security System.Xml
+LOCAL_MCS_FLAGS = /win32icon:mono.ico
 
 # SWF isn't quite good enough to build this yet.
 
index bf5bd1c904e560af111c0b9f312dc980f7965fa9..e7750a2c11b4b525bc791204b3f18a5404e99621 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/sgen
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml System
 PROGRAM = sgen.exe
 
 include ../../build/executable.make
index 2fccb32ad59c2b328baf0f9c6580dd532e29a446..1fc6cb2763e6cd3e6b52d59ee4b07bd7d3b92cde 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/soapsuds
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Runtime.Remoting.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Runtime.Remoting System
 PROGRAM = soapsuds.exe
 
 include ../../build/executable.make
index 7bd68482312e9491925aa0ebcd7e03e933e5e54e..6be257edd226798b815e1c859abc4c628edf6d16 100644 (file)
@@ -11,30 +11,21 @@ LOCAL_MCS_FLAGS = \
        -resource:$(dbmetal_src)/Language/EnglishWords.txt,$(ns).EnglishWords.txt \
        -resource:$(dbmetal_src)/Language/FrenchWords.txt,$(ns).FrenchWords.txt   \
        -resource:$(dbmetal_src)/Language/GermanWords.txt,$(ns).GermanWords.txt   \
-       -r:System.Configuration.dll                                             \
-       -r:System.Core.dll                                                      \
-       -r:System.Data.dll                                                      \
-       -r:System.Data.Linq.dll                                                 \
-       -r:System.Xml.dll \
-       -r:System.dll
+       -publicsign
 
+LIB_REFS = System.Configuration System.Core System.Data System.Data.Linq System.Xml System
+       
 SQLMETAL_RESOURCES = \
        $(dbmetal_src)/Language/EnglishWords.txt \
        $(dbmetal_src)/Language/FrenchWords.txt  \
        $(dbmetal_src)/Language/GermanWords.txt
 
-SQLMETAL_TEST_FILES = \
-       Test/AssemblyInfo.cs
-
 EXTRA_DISTFILES = \
-       $(SQLMETAL_RESOURCES) \
-       $(SQLMETAL_TEST_FILES)
+       $(SQLMETAL_RESOURCES)
 
 PROGRAM = sqlmetal.exe
 
 $(PROGRAM) : Makefile $(SQLMETAL_RESOURCES)
 
-HAS_NUNIT_TEST = yes
-
 include ../../build/executable.make
 
diff --git a/mcs/tools/sqlmetal/Test/.gitattributes b/mcs/tools/sqlmetal/Test/.gitattributes
deleted file mode 100644 (file)
index f7d8287..0000000
+++ /dev/null
@@ -1 +0,0 @@
-/AssemblyInfo.cs -crlf
diff --git a/mcs/tools/sqlmetal/Test/AssemblyInfo.cs b/mcs/tools/sqlmetal/Test/AssemblyInfo.cs
deleted file mode 100644 (file)
index 5ff26a5..0000000
+++ /dev/null
@@ -1,42 +0,0 @@
-//\r
-// AssemblyInfo.cs\r
-//\r
-// Author:\r
-//   Jonathan Pryor  <jpryor@novell.com>\r
-//\r
-// Copyright (C) 2009 Novell, Inc.\r
-//\r
-\r
-//\r
-// Permission is hereby granted, free of charge, to any person obtaining\r
-// a copy of this software and associated documentation files (the\r
-// "Software"), to deal in the Software without restriction, including\r
-// without limitation the rights to use, copy, modify, merge, publish,\r
-// distribute, sublicense, and/or sell copies of the Software, and to\r
-// permit persons to whom the Software is furnished to do so, subject to\r
-// the following conditions:\r
-// \r
-// The above copyright notice and this permission notice shall be\r
-// included in all copies or substantial portions of the Software.\r
-// \r
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,\r
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF\r
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND\r
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE\r
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION\r
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION\r
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\r
-//\r
-\r
-using System;\r
-using System.Reflection;\r
-using System.Runtime.CompilerServices;\r
-\r
-[assembly: AssemblyTitle ("sqlmetal_test")]\r
-[assembly: AssemblyDescription ("sqlmetal.exe Unit Tests")]\r
-[assembly: AssemblyDefaultAlias ("SqlMetal_test.dll")]\r
-\r
-[assembly: CLSCompliant (true)]\r
-\r
-// Unit tests needs access to the DbLinq internals\r
-\r
index 042e97b92a31ca95e2b8554eccc8ed8146943ea5..88ad1f8d9b5cca744ae8ae233bec051b2a7d20fa 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/SqlSharp
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Xml.dll -r:System.Data.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System System.Xml System.Data
 PROGRAM = sqlsharp.exe
 
 EXTRA_DISTFILES = README
index cf174fe39794ccb28d2282f4c16f50d258cea44d..b194a5b144d5fbda9d79c1408da449490ca2134f 100644 (file)
@@ -2,14 +2,8 @@ thisdir = tools/svcutil
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = \
-       -r:System.Core.dll \
-       -r:System.Runtime.Serialization.dll \
-       -r:System.ServiceModel.dll \
-       -r:System.Web.Services.dll \
-       -r:System.Configuration.dll \
-       -r:System.dll \
-       -r:System.Xml.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Core System.Runtime.Serialization System.ServiceModel System.Web.Services System.Configuration System System.Xml
        
 PROGRAM = svcutil.exe
 
index bfc24a16c459ce42a05b821a4e7ef530b6024f46..c364223deb0419d3df72bd4ed047101a2d167dd7 100644 (file)
@@ -3,10 +3,8 @@ SUBDIRS =
 DEP_DIRS = linker
 include ../../build/rules.make
 
-CECIL = $(topdir)/class/lib/$(PROFILE)/Mono.Cecil.dll
-LINKER = $(topdir)/class/lib/$(PROFILE)/monolinker.exe
-
-LOCAL_MCS_FLAGS = -r:System.dll -r:System.Core.dll -r:System.Xml.dll -r:$(LINKER) -r:$(CECIL)
+LOCAL_MCS_FLAGS = -r:$(topdir)/class/lib/$(PROFILE)/monolinker.exe
+LIB_REFS = System System.Core System.Xml Mono.Cecil
 
 LIBRARY = Mono.Tuner.dll
 
index f60bd4dc20d4c1cd61681928bdddd067640e222d..8291f0b21c951803f3f3105c216c8f8a431e8681 100644 (file)
@@ -4,6 +4,7 @@ include ../../build/rules.make
 
 PROGRAM = txt2sr.exe
 
+LIB_REFS = System
 LOCAL_MCS_FLAGS =
 
 include ../../build/executable.make
index bf30b54e865782da427ced9d9f0753168f2c6a7f..7a103203f23c7d6c877e04d6ea779d397c83ab84 100644 (file)
@@ -38,6 +38,7 @@ public class Program
                public bool ShowHelp { get; set; }
                public bool Verbose { get; set; }
                public List<string> ResourcesStrings { get; }
+               public bool IgnoreSemicolon { get; set; }
 
                public CmdOptions ()
                {
@@ -55,7 +56,9 @@ public class Program
                        { "h|help",  "Display available options", 
                                v => options.ShowHelp = v != null },
                        { "v|verbose",  "Use verbose output", 
-                               v => options.Verbose = v != null },                     
+                               v => options.Verbose = v != null },
+                       { "ignore-semicolon", "Reads lines starting with semicolon",
+                               v => options.IgnoreSemicolon = v != null },
                };
 
                List<string> extra;
@@ -142,14 +145,22 @@ public class Program
 
                        foreach (var l in File.ReadLines (fileName)) {
                                var line = l.Trim ();
-                               if (line.Length == 0 || line [0] == '#' || line [0] == ';')
+                               if (line.Length == 0 || line [0] == '#')
                                        continue;
 
+                               int start = 0;
+                               if (line [0] == ';') {
+                                       if (!options.IgnoreSemicolon)
+                                               continue;
+
+                                       start = 1;
+                               }
+
                                var epos = line.IndexOf ('=');
                                if (epos < 0)
                                        continue;
 
-                               var key = line.Substring (0, epos).Trim ();
+                               var key = line.Substring (start, epos - start).Trim ();
                                if (key.Contains (" "))
                                        continue;
 
index 786c81885f058917cf44cce45d1416c33a07b8ea..293cf9d2811497344bac95184a292e9936e12289 100644 (file)
@@ -2,7 +2,8 @@ thisdir = tools/wsdl
 SUBDIRS = 
 include ../../build/rules.make
 
-LOCAL_MCS_FLAGS = -r:System.Xml.dll -r:System.Web.Services.dll -r:System.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = System.Xml System.Web.Services System
 
 PROGRAM = wsdl.exe
 
index 0ca5126a6d42fd4da33a7267f4956c5f57f14441..70457756436001b8c749fe9c846bd6e0a218c05c 100644 (file)
@@ -5,7 +5,8 @@ NO_TESTS = yes
 
 include xbuild.make
 
-LOCAL_MCS_FLAGS = -r:$(XBUILD_FRAMEWORK) -r:$(XBUILD_UTILITIES) -r:$(XBUILD_ENGINE) -r:$(XBUILD_MSTASKS) -r:System.dll -r:System.Core.dll
+LOCAL_MCS_FLAGS =
+LIB_REFS = $(XBUILD_FRAMEWORK) $(XBUILD_UTILITIES) $(XBUILD_ENGINE) $(XBUILD_MSTASKS) $(PARENT_PROFILE)System $(PARENT_PROFILE)System.Core
 PROGRAM = xbuild.exe
 
 include ../../build/executable.make
index bf44c515970b467421ac6bcb6a1a6df5874fd203..44ac70d2f963f328fd8bb2ad840912446e262454 100644 (file)
@@ -510,8 +510,8 @@ namespace Mono.XBuild.CommandLine {
                                if (solutionTarget.Configuration == targetInfo.Key.Configuration &&
                                                solutionTarget.Platform == targetInfo.Key.Platform) {
                                        solutionConfigurationContents.AppendFormat (
-                                                       "<ProjectConfiguration Project=\"{0}\">{1}|{2}</ProjectConfiguration>",
-                                       guid.ToString ("B").ToUpper (), targetInfo.Value.Configuration, targetInfo.Value.Platform);
+                                                       "<ProjectConfiguration Project=\"{0}\" AbsolutePath=\"{1}\">{2}|{3}</ProjectConfiguration>",
+                                                       guid.ToString ("B").ToUpper (), projectInfo.FileName, targetInfo.Value.Configuration, targetInfo.Value.Platform);
                                }
                        }
                }
index 1d111a1cf66d3201a71ed68f67c803fbcf239884..2cd20a10c0bd3c5f8590ceee644213579404d36b 100644 (file)
@@ -54,7 +54,7 @@
        <Target
                Name="CoreCompile"
                Inputs="$(MSBuildAllProjects);@(Compile);@(ManifestResourceWithNoCulture);@(ManifestNonResxWithNoCultureOnDisk);@(CompiledLicenseFile);
-                       $(KeyOriginatorFile);@(ReferencePath);$(Win32Icon);$(Win32Resource)"
+                       $(KeyOriginatorFile);@(ReferencePath);$(ApplicationIcon);$(Win32Resource)"
                Outputs="@(DocFileItem);@(IntermediateAssembly)"
                DependsOnTargets="$(CoreCompileDependsOn)"
        >
index 1d111a1cf66d3201a71ed68f67c803fbcf239884..2cd20a10c0bd3c5f8590ceee644213579404d36b 100644 (file)
@@ -54,7 +54,7 @@
        <Target
                Name="CoreCompile"
                Inputs="$(MSBuildAllProjects);@(Compile);@(ManifestResourceWithNoCulture);@(ManifestNonResxWithNoCultureOnDisk);@(CompiledLicenseFile);
-                       $(KeyOriginatorFile);@(ReferencePath);$(Win32Icon);$(Win32Resource)"
+                       $(KeyOriginatorFile);@(ReferencePath);$(ApplicationIcon);$(Win32Resource)"
                Outputs="@(DocFileItem);@(IntermediateAssembly)"
                DependsOnTargets="$(CoreCompileDependsOn)"
        >
index 29bd5d826aed56752aab8e74daa46868be68ec70..0c57501e5b44f04ae88f7bf3c499f15f117e583f 100644 (file)
@@ -23,7 +23,7 @@
        <Target
                Name="CoreCompile"
                Inputs="$(MSBuildAllProjects);@(Compile);@(ManifestResourceWithNoCulture);@(ManifestNonResxWithNoCultureOnDisk);@(CompiledLicenseFile);
-                       $(KeyOriginatorFile);@(ReferencePath);$(Win32Icon);$(Win32Resource)"
+                       $(KeyOriginatorFile);@(ReferencePath);$(ApplicationIcon);$(Win32Resource)"
                Outputs="@(DocFileItem);@(IntermediateAssembly)"
                DependsOnTargets="$(CoreCompileDependsOn)"
        >
index 29bd5d826aed56752aab8e74daa46868be68ec70..0c57501e5b44f04ae88f7bf3c499f15f117e583f 100644 (file)
@@ -23,7 +23,7 @@
        <Target
                Name="CoreCompile"
                Inputs="$(MSBuildAllProjects);@(Compile);@(ManifestResourceWithNoCulture);@(ManifestNonResxWithNoCultureOnDisk);@(CompiledLicenseFile);
-                       $(KeyOriginatorFile);@(ReferencePath);$(Win32Icon);$(Win32Resource)"
+                       $(KeyOriginatorFile);@(ReferencePath);$(ApplicationIcon);$(Win32Resource)"
                Outputs="@(DocFileItem);@(IntermediateAssembly)"
                DependsOnTargets="$(CoreCompileDependsOn)"
        >
index 1d111a1cf66d3201a71ed68f67c803fbcf239884..2cd20a10c0bd3c5f8590ceee644213579404d36b 100644 (file)
@@ -54,7 +54,7 @@
        <Target
                Name="CoreCompile"
                Inputs="$(MSBuildAllProjects);@(Compile);@(ManifestResourceWithNoCulture);@(ManifestNonResxWithNoCultureOnDisk);@(CompiledLicenseFile);
-                       $(KeyOriginatorFile);@(ReferencePath);$(Win32Icon);$(Win32Resource)"
+                       $(KeyOriginatorFile);@(ReferencePath);$(ApplicationIcon);$(Win32Resource)"
                Outputs="@(DocFileItem);@(IntermediateAssembly)"
                DependsOnTargets="$(CoreCompileDependsOn)"
        >
index 7247c7f8b0d1b04d7f52adefd0962d68fff07bc1..cda9d9b0e61b012485cc2b2ac2a17379bda9d1c9 100644 (file)
@@ -6,13 +6,13 @@ ifeq (14.0, $(XBUILD_VERSION))
 NAME_SUFFIX = .Core
 endif
 
-XBUILD_FRAMEWORK := $(topdir)/class/lib/$(PROFILE)/Microsoft.Build.Framework.dll
-XBUILD_ENGINE := $(topdir)/class/lib/$(PROFILE)/Microsoft.Build.Engine.dll
-XBUILD_UTILITIES := $(topdir)/class/lib/$(PROFILE)/Microsoft.Build.Utilities$(NAME_SUFFIX).dll
-XBUILD_TASKS := $(topdir)/class/lib/$(PROFILE)/Mono.XBuild.Tasks.dll
-XBUILD_MSTASKS := $(topdir)/class/lib/$(PROFILE)/Microsoft.Build.Tasks$(NAME_SUFFIX).dll
+XBUILD_FRAMEWORK := Microsoft.Build.Framework
+XBUILD_ENGINE := Microsoft.Build.Engine
+XBUILD_UTILITIES := Microsoft.Build.Utilities$(NAME_SUFFIX)
+XBUILD_TASKS := Mono.XBuild.Tasks
+XBUILD_MSTASKS := Microsoft.Build.Tasks$(NAME_SUFFIX)
 ifeq (14.0, $(XBUILD_VERSION))
-XBUILD_MSTASKS := $(topdir)/class/lib/$(PROFILE)/Microsoft.Build.Tasks.Core.dll
+XBUILD_MSTASKS := Microsoft.Build.Tasks.Core
 endif
 
 XBUILD_ASSEMBLY_VERSION = $(XBUILD_VERSION).0.0
index 181913f5751c9b68b459919dc5c911dc96f1a0da..26d73ce31c49214d27052cc77e2f929f8b436829 100644 (file)
@@ -11,6 +11,7 @@
  * 
  * Copyright (C)  2000 Intel Corporation.  All rights reserved.
  * Copyright (C)  2001, 2002 Ximian, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef AMD64_H
@@ -248,6 +249,21 @@ typedef union {
                x86_reg_emit ((inst), (dreg), (reg));   \
        } while (0)
 
+#define amd64_test_reg_imm_size_body(inst,reg,imm,size) \
+       do { \
+               amd64_codegen_pre(inst); \
+               amd64_emit_rex ((inst),(size),0,0,(reg)); \
+               if ((reg) == AMD64_RAX) { \
+                       *(inst)++ = (unsigned char)0xa9; \
+               } \
+               else { \
+                       *(inst)++ = (unsigned char)0xf7;        \
+                       x86_reg_emit((inst), 0, (reg)); \
+               } \
+               x86_imm_emit32((inst), (imm));  \
+               amd64_codegen_post(inst); \
+       } while (0)
+
 #if defined(__default_codegen__)
 
 #define amd64_alu_reg_imm_size(inst,opc,reg,imm,size) \
@@ -256,6 +272,9 @@ typedef union {
 #define amd64_alu_reg_reg_size(inst,opc,dreg,reg,size) \
                amd64_alu_reg_reg_size_body((inst), (opc), (dreg), (reg), (size))
 
+#define amd64_test_reg_imm_size(inst, reg, imm, size) \
+               amd64_test_reg_imm_size_body(inst, reg, imm, size)
+
 #elif defined(__native_client_codegen__)
 /* NaCl modules may not directly update RSP or RBP other than direct copies */
 /* between them. Instead the lower 4 bytes are updated and then added to R15 */
@@ -297,6 +316,8 @@ typedef union {
 
 #define amd64_alu_reg_reg(inst,opc,dreg,reg) amd64_alu_reg_reg_size ((inst),(opc),(dreg),(reg),8)
 
+#define amd64_test_reg_imm(inst,reg,imm) amd64_test_reg_imm_size(inst,reg,imm,8)
+
 #define amd64_alu_reg_membase_size(inst,opc,reg,basereg,disp,size) \
        do { \
                amd64_codegen_pre(inst);                                                  \
@@ -1464,7 +1485,7 @@ typedef union {
 #define amd64_alu_reg8_reg8_size(inst,opc,dreg,reg,is_dreg_h,is_reg_h,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),(dreg),0,(reg)); x86_alu_reg8_reg8((inst),(opc),((dreg)&0x7),((reg)&0x7),(is_dreg_h),(is_reg_h)); amd64_codegen_post(inst); } while (0)
 #define amd64_alu_reg_mem_size(inst,opc,reg,mem,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),0,0,(reg)); x86_alu_reg_mem((inst),(opc),((reg)&0x7),(mem)); amd64_codegen_post(inst); } while (0)
 //#define amd64_alu_reg_membase_size(inst,opc,reg,basereg,disp,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),(reg),0,(basereg)); x86_alu_reg_membase((inst),(opc),((reg)&0x7),((basereg)&0x7),(disp)); amd64_codegen_post(inst); } while (0)
-#define amd64_test_reg_imm_size(inst,reg,imm,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),0,0,(reg)); x86_test_reg_imm((inst),((reg)&0x7),(imm)); amd64_codegen_post(inst); } while (0)
+//#define amd64_test_reg_imm_size(inst,reg,imm,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),0,0,(reg)); x86_test_reg_imm((inst),((reg)&0x7),(imm)); amd64_codegen_post(inst); } while (0)
 #define amd64_test_mem_imm_size(inst,mem,imm,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),0,0,0); x86_test_mem_imm((inst),(mem),(imm)); amd64_codegen_post(inst); } while (0)
 #define amd64_test_membase_imm_size(inst,basereg,disp,imm,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),0,0,(basereg)); x86_test_membase_imm((inst),((basereg)&0x7),(disp),(imm)); amd64_codegen_post(inst); } while (0)
 #define amd64_test_reg_reg_size(inst,dreg,reg,size) do { amd64_codegen_pre(inst); amd64_emit_rex ((inst),(size),(dreg),0,(reg)); x86_test_reg_reg((inst),((dreg)&0x7),((reg)&0x7)); amd64_codegen_post(inst); } while (0)
@@ -1709,7 +1730,7 @@ typedef union {
 #define amd64_alu_reg8_reg8(inst,opc,dreg,reg,is_dreg_h,is_reg_h) amd64_alu_reg8_reg8_size(inst,opc,dreg,reg,is_dreg_h,is_reg_h,8)
 #define amd64_alu_reg_mem(inst,opc,reg,mem) amd64_alu_reg_mem_size(inst,opc,reg,mem,8)
 #define amd64_alu_reg_membase(inst,opc,reg,basereg,disp) amd64_alu_reg_membase_size(inst,opc,reg,basereg,disp,8)
-#define amd64_test_reg_imm(inst,reg,imm) amd64_test_reg_imm_size(inst,reg,imm,8)
+//#define amd64_test_reg_imm(inst,reg,imm) amd64_test_reg_imm_size(inst,reg,imm,8)
 #define amd64_test_mem_imm(inst,mem,imm) amd64_test_mem_imm_size(inst,mem,imm,8)
 #define amd64_test_membase_imm(inst,basereg,disp,imm) amd64_test_membase_imm_size(inst,basereg,disp,imm,8)
 #define amd64_test_reg_reg(inst,dreg,reg) amd64_test_reg_reg_size(inst,dreg,reg,8)
index 3ee083f8010ffdf7bad83cc527f8d32e078e6b00..1af30c6b21bb516a2466cc6d4f5bc72118884228 100644 (file)
@@ -3,6 +3,7 @@
  * Copyright (c) 2002-2003 Sergey Chaban <serge@wildwestsoftware.com>
  * Copyright 2005-2011 Novell Inc
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 
index 8b56b00dbbee462d56c19c9089a64aae9687403a..edf558da2995f17b8e5663b0a4656bfc76576ec9 100644 (file)
@@ -1,6 +1,7 @@
 //
 // Copyright 2011 Xamarin Inc
 //
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 
 #ifndef __MONO_ARM_VFP_CODEGEN_H__
 #define __MONO_ARM_VFP_CODEGEN_H__
index 427c4fc9f6066e5670172dc81c3dac0dafc52747..e43ac7763f36a4873ede1048ece176a9d8dbc0e8 100644 (file)
@@ -2,6 +2,7 @@
  * ARM CodeGen\r
  * XScale WirelessMMX extensions\r
  * Copyright 2002 Wild West Software\r
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.\r
  */\r
 \r
 #ifndef __WMMX_H__\r
index 259ff9674072a36c39df092a39a1b3a8eca25148..6ca4da6d88127686f16fe2ac70c759a8839a6f4e 100644 (file)
@@ -1,3 +1,852 @@
-#include "../../../../mono-extensions/mono/arch/arm64/arm64-codegen.h"
+/*
+ * arm64-codegen.h: ARM64 code generation macros
+ *
+ * Author:
+ *   Zoltan Varga (vargaz@gmail.com)
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
 
+#ifndef __ARM64_CODEGEN_H__
+#define __ARM64_CODEGEN_H__
 
+#include <glib.h>
+
+enum {
+       ARMREG_R0 = 0,
+       ARMREG_R1 = 1,
+       ARMREG_R2 = 2,
+       ARMREG_R3 = 3,
+       ARMREG_R4 = 4,
+       ARMREG_R5 = 5,
+       ARMREG_R6 = 6,
+       ARMREG_R7 = 7,
+       ARMREG_R8 = 8,
+       ARMREG_R9 = 9,
+       ARMREG_R10 = 10,
+       ARMREG_R11 = 11,
+       ARMREG_R12 = 12,
+       ARMREG_R13 = 13,
+       ARMREG_R14 = 14,
+       ARMREG_R15 = 15,
+       ARMREG_R16 = 16,
+       ARMREG_R17 = 17,
+       ARMREG_R18 = 18,
+       ARMREG_R19 = 19,
+       ARMREG_R20 = 20,
+       ARMREG_R21 = 21,
+       ARMREG_R22 = 22,
+       ARMREG_R23 = 23,
+       ARMREG_R24 = 24,
+       ARMREG_R25 = 25,
+       ARMREG_R26 = 26,
+       ARMREG_R27 = 27,
+       ARMREG_R28 = 28,
+       ARMREG_R29 = 29,
+       ARMREG_R30 = 30,
+       ARMREG_SP = 31,
+       ARMREG_RZR = 31,
+
+       ARMREG_IP0 = ARMREG_R16,
+       ARMREG_IP1 = ARMREG_R17,
+       ARMREG_FP = ARMREG_R29,
+       ARMREG_LR = ARMREG_R30
+};
+
+enum {
+       ARMREG_D0 = 0,
+       ARMREG_D1 = 1,
+       ARMREG_D2 = 2,
+       ARMREG_D3 = 3,
+       ARMREG_D4 = 4,
+       ARMREG_D5 = 5,
+       ARMREG_D6 = 6,
+       ARMREG_D7 = 7,
+       ARMREG_D8 = 8,
+       ARMREG_D9 = 9,
+       ARMREG_D10 = 10,
+       ARMREG_D11 = 11,
+       ARMREG_D12 = 12,
+       ARMREG_D13 = 13,
+       ARMREG_D14 = 14,
+       ARMREG_D15 = 15,
+       ARMREG_D16 = 16,
+       ARMREG_D17 = 17,
+       ARMREG_D18 = 18,
+       ARMREG_D19 = 19,
+       ARMREG_D20 = 20,
+       ARMREG_D21 = 21,
+       ARMREG_D22 = 22,
+       ARMREG_D23 = 23,
+       ARMREG_D24 = 24,
+       ARMREG_D25 = 25,
+       ARMREG_D26 = 26,
+       ARMREG_D27 = 27,
+       ARMREG_D28 = 28,
+       ARMREG_D29 = 29,
+       ARMREG_D30 = 30,
+       ARMREG_D31 = 31
+};
+
+typedef enum {
+       ARMCOND_EQ = 0x0,          /* Equal; Z = 1 */
+       ARMCOND_NE = 0x1,          /* Not equal, or unordered; Z = 0 */
+       ARMCOND_CS = 0x2,          /* Carry set; C = 1 */
+       ARMCOND_HS = ARMCOND_CS,   /* Unsigned higher or same; */
+       ARMCOND_CC = 0x3,          /* Carry clear; C = 0 */
+       ARMCOND_LO = ARMCOND_CC,   /* Unsigned lower */
+       ARMCOND_MI = 0x4,          /* Negative; N = 1 */
+       ARMCOND_PL = 0x5,          /* Positive or zero; N = 0 */
+       ARMCOND_VS = 0x6,          /* Overflow; V = 1 */
+       ARMCOND_VC = 0x7,          /* No overflow; V = 0 */
+       ARMCOND_HI = 0x8,          /* Unsigned higher; C = 1 && Z = 0 */
+       ARMCOND_LS = 0x9,          /* Unsigned lower or same; C = 0 || Z = 1 */
+       ARMCOND_GE = 0xA,          /* Signed greater than or equal; N = V */
+       ARMCOND_LT = 0xB,          /* Signed less than; N != V */
+       ARMCOND_GT = 0xC,          /* Signed greater than; Z = 0 && N = V */
+       ARMCOND_LE = 0xD,          /* Signed less than or equal; Z = 1 || N != V */
+       ARMCOND_AL = 0xE,          /* Always */
+       ARMCOND_NV = 0xF,          /* Never */
+} ARMCond;
+
+typedef enum {
+       ARMSHIFT_LSL = 0x0,
+       ARMSHIFT_LSR = 0x1,
+       ARMSHIFT_ASR = 0x2
+} ARMShift;
+
+typedef enum {
+       ARMSIZE_B = 0x0,
+       ARMSIZE_H = 0x1,
+       ARMSIZE_W = 0x2,
+       ARMSIZE_X = 0x3
+} ARMSize;
+
+#define arm_emit(p, ins) do { *(guint32*)(p) = (ins); (p) += 4; } while (0)
+
+/* Overwrite bits [offset,offset+nbits] with value */
+static G_GNUC_UNUSED inline void
+arm_set_ins_bits (void *p, int offset, int nbits, guint32 value)
+{
+       *(guint32*)p = (*(guint32*)p & ~(((1 << nbits) - 1) << offset)) | (value << offset);
+}
+
+/*
+ * Naming conventions for codegen macros:
+ * - 64 bit opcodes have an 'X' suffix
+ * - 32 bit opcodes have a 'W' suffix
+ * - the order of operands is the same as in assembly
+ */
+
+/*
+ * http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.ddi0487a/index.html
+ */
+
+/* Uncoditional branch (register) */
+
+// 0b1101011 == 0x6b
+#define arm_format_breg(p, opc, op2, op3, op4, rn) arm_emit ((p), (0x6b << 25) | ((opc) << 21) | ((op2) << 16) | ((op3) << 10) | ((rn) << 5) | ((op4) << 0))
+
+// 0b0000 == 0x0, 0b11111 == 0x1f
+#define arm_brx(p, reg) arm_format_breg ((p), 0x0, 0x1f, 0x0, 0x0, (reg))
+
+// 0b0001 == 0x1
+#define arm_blrx(p, reg) arm_format_breg ((p), 0x1, 0x1f, 0x0, 0x0, (reg))
+
+//0b0010 == 0x2
+#define arm_retx(p, reg) arm_format_breg ((p), 0x2, 0x1f, 0x0, 0x0, (reg))
+
+/* Unconditional branch (immeditate) */
+
+static G_GNUC_UNUSED inline gboolean
+arm_is_bl_disp (void *code, void *target)
+{
+       gint64 disp = ((char*)(target) - (char*)(code)) / 4;
+
+       return (disp > -(1 << 25)) && (disp < (1 << 25));
+}
+
+static G_GNUC_UNUSED inline unsigned int
+arm_get_disp (void *p, void *target)
+{
+       unsigned int disp = ((char*)target - (char*)p) / 4;
+
+       if (target)
+               g_assert (arm_is_bl_disp (p, target));
+
+       return (disp & 0x3ffffff);
+}
+
+// 0b00101 == 0x5
+#define arm_b(p, target) arm_emit (p, (0x0 << 31) | (0x5 << 26) | ((arm_get_disp ((p), (target)) << 0)))
+
+#define arm_bl(p, target) arm_emit (p, (0x1 << 31) | (0x5 << 26) | ((arm_get_disp ((p), (target)) << 0)))
+
+/* Conditional branch */
+
+static G_GNUC_UNUSED inline gboolean
+arm_is_disp19 (void *code, void *target)
+{
+       gint64 disp = ((char*)(target) - (char*)(code)) / 4;
+
+       return (disp > -(1 << 18)) && (disp < (1 << 18));
+}
+
+static G_GNUC_UNUSED inline unsigned int
+arm_get_disp19 (void *p, void *target)
+{
+       unsigned int disp = ((char*)target - (char*)p) / 4;
+
+       if (target)
+               g_assert (arm_is_disp19 (p, target));
+
+       return (disp & 0x7ffff);
+}
+
+// 0b0101010 == 0x2a
+#define arm_format_condbr(p, o1, o0, cond, disp) arm_emit ((p), (0x2a << 25) | ((o1) << 24) | ((disp) << 5) | ((o0) << 4) | ((cond) << 0))
+#define arm_get_bcc_cond(p) ((*(guint32*)p) & 0xf)
+
+#define arm_bcc(p, cond, target) arm_format_condbr ((p), 0x0, 0x0, (cond), arm_get_disp19 ((p), (target)))
+
+// 0b011010 == 0x1a
+#define arm_format_cmpbr(p, sf, op, rt, target) arm_emit ((p), ((sf) << 31) | (0x1a << 25) | ((op) << 24) | (arm_get_disp19 ((p), (target)) << 5) | ((rt) << 0))
+
+#define arm_set_cbz_target(p, target) arm_set_ins_bits (p, 5, 19, arm_get_disp19 ((p), (target)))
+
+#define arm_cbzx(p, rt, target) arm_format_cmpbr ((p), 0x1, 0x0, (rt), (target))
+#define arm_cbzw(p, rt, target) arm_format_cmpbr ((p), 0x0, 0x0, (rt), (target))
+
+#define arm_cbnzx(p, rt, target) arm_format_cmpbr ((p), 0x1, 0x1, (rt), (target))
+#define arm_cbnzw(p, rt, target) arm_format_cmpbr ((p), 0x0, 0x1, (rt), (target))
+
+static G_GNUC_UNUSED inline unsigned int
+arm_get_disp15 (void *p, void *target)
+{
+       unsigned int disp = ((char*)target - (char*)p) / 4;
+       return (disp & 0x7fff);
+}
+
+// 0b011011 == 0x1b
+#define arm_format_tbimm(p, op, rt, bit, target) arm_emit ((p), ((((bit) >> 5) & 1) << 31) | (0x1b << 25) | ((op) << 24) | (((bit) & 0x1f) << 19) | (arm_get_disp15 ((p), (target)) << 5) | ((rt) << 0))
+
+#define arm_tbz(p, rt, bit, target) arm_format_tbimm ((p), 0x0, (rt), (bit), (target))
+#define arm_tbnz(p, rt, bit, target) arm_format_tbimm ((p), 0x1, (rt), (bit), (target))
+
+/* Memory access */
+
+#define arm_is_pimm12_scaled(pimm,size) ((pimm) >= 0 && (pimm) / (size) <= 0xfff && ((pimm) % (size)) == 0)
+
+static G_GNUC_UNUSED unsigned int
+arm_encode_pimm12 (int pimm, int size)
+{
+       g_assert (arm_is_pimm12_scaled (pimm, size));
+       return ((unsigned int)(pimm / size)) & 0xfff;
+}
+
+#define arm_is_strb_imm(pimm) arm_is_pimm12_scaled((pimm), 1)
+#define arm_is_strh_imm(pimm) arm_is_pimm12_scaled((pimm), 2)
+#define arm_is_strw_imm(pimm) arm_is_pimm12_scaled((pimm), 4)
+#define arm_is_strx_imm(pimm) arm_is_pimm12_scaled((pimm), 8)
+
+/* Load/Store register + scaled immediate */
+/* No pre-index/post-index yet */
+#define arm_format_mem_imm(p, size, opc, rt, rn, pimm, scale) arm_emit ((p), ((size) << 30) | (0x39 << 24) | ((opc) << 22) | (arm_encode_pimm12 ((pimm), (scale)) << 10) | ((rn) << 5) | ((rt) << 0))
+
+/* C5.6.83 LDR (immediate) */
+#define arm_ldrx(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_X, 0x1, (rt), (rn), (pimm), 8)
+#define arm_ldrw(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_W, 0x1, (rt), (rn), (pimm), 4)
+/* C5.6.86 LDRB (immediate) */
+#define arm_ldrb(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_B, 0x1, (rt), (rn), (pimm), 1)
+/* C5.6.88 LDRH (immediate) */
+#define arm_ldrh(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_H, 0x1, (rt), (rn), (pimm), 2)
+/* C5.6.90 LDRSB (immediate) */
+#define arm_ldrsbx(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_B, 0x2, (rt), (rn), (pimm), 1)
+#define arm_ldrsbw(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_B, 0x3, (rt), (rn), (pimm), 1)
+/* C5.6.92 LDRSH (immediate) */
+#define arm_ldrshx(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_H, 0x2, (rt), (rn), (pimm), 2)
+#define arm_ldrshw(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_H, 0x3, (rt), (rn), (pimm), 2)
+/* C5.6.94 LDRSW (immediate) */
+#define arm_ldrswx(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_W, 0x2, (rt), (rn), (pimm), 4)
+
+/* C5.6.178 STR (immediate) */
+#define arm_strx(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_X, 0x0, (rt), (rn), (pimm), 8)
+#define arm_strw(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_W, 0x0, (rt), (rn), (pimm), 4)
+/* C5.6.182 STR (immediate) */
+#define arm_strh(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_H, 0x0, (rt), (rn), (pimm), 2)
+#define arm_strb(p, rt, rn, pimm) arm_format_mem_imm (p, ARMSIZE_B, 0x0, (rt), (rn), (pimm), 1)
+
+/* C3.3.9 Load/store register (immediate post-indexed) */
+static G_GNUC_UNUSED unsigned int
+arm_encode_simm9 (int simm)
+{
+       g_assert (simm >= -256 && simm <= 255);
+       return ((unsigned int)simm) & 0x1ff;
+}
+
+#define arm_format_mem_imm_post(p, size, V, opc, rt, rn, simm) arm_emit ((p), ((size) << 30) | (0x7 << 27) | ((V) << 26) | (0x0 << 24) | ((opc) << 22) | (arm_encode_simm9 ((simm)) << 12) | (0x1 << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_ldrx_post(p, rt, rn, simm) arm_format_mem_imm_post (p, ARMSIZE_X, 0x0, 0x1, (rt), (rn), (simm))
+#define arm_ldrw_post(p, rt, rn, simm) arm_format_mem_imm_post (p, ARMSIZE_W, 0x0, 0x1, (rt), (rn), (simm))
+
+#define arm_strx_post(p, rt, rn, simm) arm_format_mem_imm_post (p, ARMSIZE_X, 0x0, 0x0, (rt), (rn), (simm))
+#define arm_strw_post(p, rt, rn, simm) arm_format_mem_imm_post (p, ARMSIZE_W, 0x0, 0x0, (rt), (rn), (simm))
+
+/* C3.3.9 Load/store register (immediate pre-indexed) */
+#define arm_format_mem_imm_pre(p, size, V, opc, rt, rn, simm) arm_emit ((p), ((size) << 30) | (0x7 << 27) | ((V) << 26) | (0x0 << 24) | ((opc) << 22) | (arm_encode_simm9 ((simm)) << 12) | (0x3 << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_ldrx_pre(p, rt, rn, simm) arm_format_mem_imm_pre (p, ARMSIZE_X, 0x0, 0x1, (rt), (rn), (simm))
+#define arm_ldrw_pre(p, rt, rn, simm) arm_format_mem_imm_pre (p, ARMSIZE_W, 0x0, 0x1, (rt), (rn), (simm))
+
+#define arm_strx_pre(p, rt, rn, simm) arm_format_mem_imm_pre (p, ARMSIZE_X, 0x0, 0x0, (rt), (rn), (simm))
+#define arm_strw_pre(p, rt, rn, simm) arm_format_mem_imm_pre (p, ARMSIZE_W, 0x0, 0x0, (rt), (rn), (simm))
+
+/* Load/Store register + register */
+/* No extend/scale yet */
+#define arm_format_mem_reg(p, size, opc, rt, rn, rm) arm_emit ((p), ((size) << 30) | (0x38 << 24) | ((opc) << 22) | (0x1 << 21) | ((rm) << 16) | (0x3 << 13) | (0 << 12) | (0x2 << 10) | ((rn) << 5) | ((rt) << 0))
+
+/* C5.6.85 LDR (register) */
+#define arm_ldrx_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_X, 0x1, (rt), (rn), (rm))
+#define arm_ldrw_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_W, 0x1, (rt), (rn), (rm))
+/* C5.6.87 LDRB (register) */
+#define arm_ldrb_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_B, 0x1, (rt), (rn), (rm))
+/* C5.6.88 LDRH (register) */
+#define arm_ldrh_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_H, 0x1, (rt), (rn), (rm))
+/* C5.6.91 LDRSB (register) */
+#define arm_ldrsbx_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_B, 0x2, (rt), (rn), (rm))
+#define arm_ldrsbw_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_B, 0x3, (rt), (rn), (rm))
+/* C5.6.93 LDRSH (register) */
+#define arm_ldrshx_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_H, 0x2, (rt), (rn), (rm))
+#define arm_ldrshw_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_H, 0x3, (rt), (rn), (rm))
+/* C5.6.96 LDRSW (register) */
+#define arm_ldrswx_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_W, 0x2, (rt), (rn), (rm))
+
+/* C5.6.179 STR (register) */
+#define arm_strx_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_X, 0x0, (rt), (rn), (rm))
+#define arm_strw_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_W, 0x0, (rt), (rn), (rm))
+/* C5.6.181 STRB (register) */
+#define arm_strb_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_B, 0x0, (rt), (rn), (rm))
+/* C5.6.183 STRH (register) */
+#define arm_strh_reg(p, rt, rn, rm) arm_format_mem_reg ((p), ARMSIZE_H, 0x0, (rt), (rn), (rm))
+
+/* PC relative */
+
+/* C5.6.84 LDR (literal) */
+
+#define arm_get_ldr_lit_reg(p) (*(guint32*)(p) & 0x1f)
+
+#define arm_ldrx_lit(p, rt, target) arm_emit ((p), (0x01 << 30) | (0x18 << 24) | (arm_get_disp19 ((p), (target)) << 5) | ((rt) << 0))
+#define arm_ldrw_lit(p, rt, target) arm_emit ((p), (0x00 << 30) | (0x18 << 24) | (arm_get_disp19 ((p), (target)) << 5) | ((rt) << 0))
+#define arm_ldrswx_lit(p, rt, target) arm_emit ((p), (0x2 << 30) | (0x18 << 24) | (arm_get_disp19 ((p), (target)) << 5) | ((rt) << 0))
+
+/* Unscaled offset */
+/* FIXME: Not yet */
+
+/* Load/Store Pair */
+
+static G_GNUC_UNUSED unsigned int
+arm_encode_imm7 (int imm, int size)
+{
+       g_assert (imm / size >= -64 && imm / size <= 63 && (imm % size) == 0);
+       return ((unsigned int)(imm / size)) & 0x7f;
+}
+
+#define arm_is_imm7_scaled(imm, size) ((imm) / (size) >= -64 && (imm) / (size) <= 63 && ((imm) % (size)) == 0)
+
+#define arm_is_ldpx_imm(imm) arm_is_imm7_scaled ((imm), 8)
+
+/* C3.3.14 */
+#define arm_format_mem_p(p, size, opc, L, rt1, rt2, rn, imm) arm_emit ((p), (opc << 30) | (0x52 << 23) | ((L) << 22) | (arm_encode_imm7 (imm, size) << 15) | ((rt2) << 10) | ((rn) << 5) | ((rt1) << 0))
+
+#define arm_ldpx(p, rt1, rt2, rn, imm) arm_format_mem_p ((p), 8, 0x2, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpw(p, rt1, rt2, rn, imm) arm_format_mem_p ((p), 4, 0x0, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpsw(p, rt1, rt2, rn, imm) arm_format_mem_p ((p), 4, 0x1, 1, (rt1), (rt2), (rn), (imm))
+#define arm_stpx(p, rt1, rt2, rn, imm) arm_format_mem_p ((p), 8, 0x2, 0, (rt1), (rt2), (rn), (imm))
+#define arm_stpw(p, rt1, rt2, rn, imm) arm_format_mem_p ((p), 4, 0x0, 0, (rt1), (rt2), (rn), (imm))
+
+/* Load/Store Pair (Pre-indexed) */
+/* C3.3.16 */
+#define arm_format_mem_p_pre(p, size, opc, L, rt1, rt2, rn, imm) arm_emit ((p), (opc << 30) | (0x53 << 23) | ((L) << 22) | (arm_encode_imm7 (imm, size) << 15) | ((rt2) << 10) | ((rn) << 5) | ((rt1) << 0))
+
+#define arm_ldpx_pre(p, rt1, rt2, rn, imm) arm_format_mem_p_pre ((p), 8, 0x2, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpw_pre(p, rt1, rt2, rn, imm) arm_format_mem_p_pre ((p), 4, 0x0, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpsw_pre(p, rt1, rt2, rn, imm) arm_format_mem_p_pre ((p), 4, 0x1, 1, (rt1), (rt2), (rn), (imm))
+#define arm_stpx_pre(p, rt1, rt2, rn, imm) arm_format_mem_p_pre ((p), 8, 0x2, 0, (rt1), (rt2), (rn), (imm))
+#define arm_stpw_pre(p, rt1, rt2, rn, imm) arm_format_mem_p_pre ((p), 4, 0x0, 0, (rt1), (rt2), (rn), (imm))
+
+/* Not an official alias */
+#define arm_pushpx (p, rt1, rt2) arm_LDPX_pre (p, rt1, rt2, ARMREG_RSP, -8)
+
+/* Load/Store Pair (Post-indexed) */
+/* C3.3.15 */
+#define arm_format_mem_p_post(p, size, opc, L, rt1, rt2, rn, imm) arm_emit ((p), (opc << 30) | (0x51 << 23) | ((L) << 22) | (arm_encode_imm7 (imm, size) << 15) | ((rt2) << 10) | ((rn) << 5) | ((rt1) << 0))
+
+#define arm_ldpx_post(p, rt1, rt2, rn, imm) arm_format_mem_p_post ((p), 8, 0x2, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpw_post(p, rt1, rt2, rn, imm) arm_format_mem_p_post ((p), 4, 0x0, 1, (rt1), (rt2), (rn), (imm))
+#define arm_ldpsw_post(p, rt1, rt2, rn, imm) arm_format_mem_p_post ((p), 4, 0x1, 1, (rt1), (rt2), (rn), (imm))
+#define arm_stpx_post(p, rt1, rt2, rn, imm) arm_format_mem_p_post ((p), 8, 0x2, 0, (rt1), (rt2), (rn), (imm))
+#define arm_stpw_post(p, rt1, rt2, rn, imm) arm_format_mem_p_post ((p), 4, 0x0, 0, (rt1), (rt2), (rn), (imm))
+
+/* Not an official alias */
+#define arm_poppx (p, rt1, rt2) arm_ldpx_post (p, rt1, rt2, ARMREG_RSP, 8)
+
+/* Load/Store Exclusive */
+#define arm_format_ldxr(p, size, rt, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x1 << 22) | (0x0 << 21) | (0x1f << 16) | (0x0 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+#define arm_format_ldxp(p, size, rt1, rt2, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x1 << 22) | (0x1 << 21) | (0x1f << 16) | (0x0 << 15) | ((rt2) << 10)| ((rn) << 5) | ((rt1) << 0))
+#define arm_format_stxr(p, size, rs, rt, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x0 << 22) | (0x0 << 21) | ((rs) << 16) | (0x0 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+#define arm_format_stxp(p, size, rs, rt1, rt2, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x0 << 22) | (0x1 << 21) | ((rs) << 16) | (0x0 << 15) | ((rt2) << 10)| ((rn) << 5) | ((rt1) << 0))
+
+#define arm_ldxrx(p, rt, rn) arm_format_ldxr ((p), ARMSIZE_X, (rt), (rn))
+#define arm_ldxrw(p, rt, rn) arm_format_ldxr ((p), ARMSIZE_W, (rt), (rn))
+#define arm_ldxrh(p, rt, rn) arm_format_ldxr ((p), ARMSIZE_H, (rt), (rn))
+#define arm_ldxrb(p, rt, rn) arm_format_ldxr ((p), ARMSIZE_B, (rt), (rn))
+#define arm_ldxpx(p, rt1, rt2, rn) arm_format_ldxp ((p), ARMSIZE_X, (rt1), (rt2), (rn))
+#define arm_ldxpw(p, rt1, rt2, rn) arm_format_ldxp ((p), ARMSIZE_W, (rt1), (rt2), (rn))
+#define arm_stxrx(p, rs, rt, rn) arm_format_stxr ((p), ARMSIZE_X, (rs), (rt), (rn))
+#define arm_stxrw(p, rs, rt, rn) arm_format_stxr ((p), ARMSIZE_W, (rs), (rt), (rn))
+#define arm_stxrh(p, rs, rt, rn) arm_format_stxr ((p), ARMSIZE_H, (rs), (rt), (rn))
+#define arm_stxrb(p, rs, rt, rn) arm_format_stxr ((p), ARMSIZE_B, (rs), (rt), (rn))
+#define arm_stxpx(p, rs, rt1, rt2, rn) arm_format_stxp ((p), ARMSIZE_X, (rs), (rt1), (rt2), (rn))
+#define arm_stxpw(p, rs, rt1, rt2, rn) arm_format_stxp ((p), ARMSIZE_W, (rs), (rt1), (rt2), (rn))
+
+/* C5.6.73 LDAR: Load-Acquire Register */
+
+#define arm_format_ldar(p, size, rt, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x1 << 23) | (0x1 << 22) | (0x0 << 21) | (0x1f << 16) | (0x1 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_ldarx(p, rt, rn) arm_format_ldar ((p), ARMSIZE_X, (rt), (rn))
+#define arm_ldarw(p, rt, rn) arm_format_ldar ((p), ARMSIZE_W, (rt), (rn))
+#define arm_ldarh(p, rt, rn) arm_format_ldar ((p), ARMSIZE_H, (rt), (rn))
+#define arm_ldarb(p, rt, rn) arm_format_ldar ((p), ARMSIZE_B, (rt), (rn))
+
+/* C5.6.169 STLR: Store-Release Register */
+
+#define arm_format_stlr(p, size, rt, rn) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x1 << 23) | (0x0 << 22) | (0x0 << 21) | (0x1f << 16) | (0x1 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_stlrx(p, rn, rt) arm_format_stlr ((p), ARMSIZE_X, (rt), (rn))
+#define arm_stlrw(p, rn, rt) arm_format_stlr ((p), ARMSIZE_W, (rt), (rn))
+#define arm_stlrh(p, rn, rt) arm_format_stlr ((p), ARMSIZE_H, (rt), (rn))
+#define arm_stlrb(p, rn, rt) arm_format_stlr ((p), ARMSIZE_B, (rt), (rn))
+
+/* C5.6.77 LDAXR */
+#define arm_format_ldaxr(p, size, rn, rt) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x1 << 22) | (0x0 << 21) | (0x1f << 16) | (0x1 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_ldaxrx(p, rt, rn) arm_format_ldaxr ((p), 0x3, (rn), (rt))
+#define arm_ldaxrw(p, rt, rn) arm_format_ldaxr ((p), 0x2, (rn), (rt))
+
+/* C5.6.173 STLXR */
+#define arm_format_stlxr(p, size, rs, rn, rt) arm_emit ((p), ((size) << 30) | (0x8 << 24) | (0x0 << 23) | (0x0 << 22) | (0x0 << 21) | ((rs) << 16) | (0x1 << 15) | (0x1f << 10) | ((rn) << 5) | ((rt) << 0))
+
+#define arm_stlxrx(p, rs, rt, rn) arm_format_stlxr ((p), 0x3, (rs), (rn), (rt))
+#define arm_stlxrw(p, rs, rt, rn) arm_format_stlxr ((p), 0x2, (rs), (rn), (rt))
+
+/* Load/Store SIMD&FP */
+
+/* C6.3.285 STR (immediate, SIMD&FP) */
+#define arm_format_strfp_imm(p, size, opc, rt, rn, pimm, scale) arm_emit ((p), ((size) << 30) | (0xf << 26) | (0x1 << 24) | ((opc) << 22) | (arm_encode_pimm12 ((pimm), (scale)) << 10) | ((rn) << 5) | ((rt) << 0))
+
+/* Store double */
+#define arm_strfpx(p, dt, xn, simm) arm_format_strfp_imm ((p), ARMSIZE_X, 0x0, (dt), (xn), (simm), 8)
+/* Store single */
+#define arm_strfpw(p, st, xn, simm) arm_format_strfp_imm ((p), ARMSIZE_W, 0x0, (st), (xn), (simm), 4)
+
+/* C6.3.166 LDR (immediate, SIMD&FP) */
+#define arm_format_ldrfp_imm(p, size, opc, rt, rn, pimm, scale) arm_emit ((p), ((size) << 30) | (0xf << 26) | (0x1 << 24) | ((opc) << 22) | (arm_encode_pimm12 ((pimm), (scale)) << 10) | ((rn) << 5) | ((rt) << 0))
+
+/* Load double */
+#define arm_ldrfpx(p, dt, xn, simm) arm_format_ldrfp_imm ((p), ARMSIZE_X, 0x1, dt, xn, simm, 8)
+/* Load single */
+#define arm_ldrfpw(p, dt, xn, simm) arm_format_ldrfp_imm ((p), ARMSIZE_W, 0x1, dt, xn, simm, 4)
+
+/* Arithmetic (immediate) */
+static G_GNUC_UNUSED inline guint32
+arm_encode_arith_imm (int imm, guint32 *shift)
+{
+       // FIXME:
+       g_assert ((imm >= 0) && (imm < 0xfff));
+       *shift = 0;
+       return (guint32)imm;
+}
+
+// FIXME:
+#define arm_is_arith_imm(imm)  (((imm) >= 0) && ((imm) < 0xfff))
+
+#define arm_format_alu_imm(p, sf, op, S, rd, rn, imm) do { \
+       guint32 _imm12, _shift; \
+       _imm12 = arm_encode_arith_imm ((imm), &_shift); arm_emit ((p), ((sf) << 31) | ((op) << 30) | ((S) << 29) | (0x11 << 24) | ((_shift) << 22) | ((_imm12) << 10) | ((rn) << 5) | ((rd) << 0)); \
+} while (0)
+
+/* rd/rn can be SP for addx/subx */
+#define arm_addx_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x1, 0x0, 0x0, (rd), (rn), (imm))
+#define arm_addw_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x0, 0x0, 0x0, (rd), (rn), (imm))
+#define arm_addsx_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x1, 0x0, 0x1, (rd), (rn), (imm))
+#define arm_addsw_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x0, 0x0, 0x1, (rd), (rn), (imm))
+#define arm_subx_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x1, 0x1, 0x0, (rd), (rn), (imm))
+#define arm_subw_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x0, 0x1, 0x0, (rd), (rn), (imm))
+#define arm_subsx_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x1, 0x1, 0x1, (rd), (rn), (imm))
+#define arm_subsw_imm(p, rd, rn, imm) arm_format_alu_imm ((p), 0x0, 0x1, 0x1, (rd), (rn), (imm))
+
+#define arm_cmpx_imm(p, rn, imm) arm_subsx_imm ((p), ARMREG_RZR, (rn), (imm))
+#define arm_cmpw_imm(p, rn, imm) arm_subsw_imm ((p), ARMREG_RZR, (rn), (imm))
+#define arm_cmnx_imm(p, rn, imm) arm_addsx_imm ((p), ARMREG_RZR, (rn), (imm))
+#define arm_cmnw_imm(p, rn, imm) arm_addsw_imm ((p), ARMREG_RZR, (rn), (imm))
+
+/* Logical (immediate) */
+
+// FIXME: imm
+#if 0
+#define arm_format_and(p, sf, opc, rd, rn, imm) arm_emit ((p), ((sf) << 31) | ((opc) << 29) | (0x24 << 23) | ((0) << 22) | ((imm) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_andx_imm(p, rd, rn, imm) arm_format_and ((p), 0x1, 0x0, (rd), (rn), (imm))
+#define arm_andw_imm(p, rd, rn, imm) arm_format_and ((p), 0x0, 0x0, (rd), (rn), (imm))
+#define arm_andsx_imm(p, rd, rn, imm) arm_format_and ((p), 0x1, 0x3, (rd), (rn), (imm))
+#define arm_andsw_imm(p, rd, rn, imm) arm_format_and ((p), 0x0, 0x3, (rd), (rn), (imm))
+#define arm_eorx_imm(p, rd, rn, imm) arm_format_and ((p), 0x1, 0x2, (rd), (rn), (imm))
+#define arm_eorw_imm(p, rd, rn, imm) arm_format_and ((p), 0x0, 0x2, (rd), (rn), (imm))
+#define arm_orrx_imm(p, rd, rn, imm) arm_format_and ((p), 0x1, 0x1, (rd), (rn), (imm))
+#define arm_orrw_imm(p, rd, rn, imm) arm_format_and ((p), 0x0, 0x1, (rd), (rn), (imm))
+
+#define arm_tstx_imm(p, rn, imm) arm_andsx_imm ((p), ARMREG_RZR, (rn), (imm))
+#define arm_tstw_imm(p, rn, imm) arm_andsw_imm ((p), ARMREG_RZR, (rn), (imm))
+#endif
+
+/* Move (wide immediate) */
+#define arm_format_mov(p, sf, opc, hw, rd, imm16) arm_emit ((p), ((sf) << 31) | ((opc) << 29) | (0x25 << 23) | ((hw) << 21) | (((guint32)(imm16) & 0xffff) << 5) | ((rd) << 0))
+
+#define arm_get_movzx_rd(p) ((*(guint32*)p) & 0x1f)
+
+#define arm_movzx(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x1, 0x2, (shift) / 16, (rd), (imm)); } while (0)
+#define arm_movzw(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x0, 0x2, (shift) / 16, (rd), (imm)); } while (0)
+#define arm_movnx(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x1, 0x0, (shift) / 16, (rd), (imm)); } while (0)
+#define arm_movnw(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x0, 0x0, (shift) / 16, (rd), (imm)); } while (0)
+#define arm_movkx(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x1, 0x3, (shift) / 16, (rd), (imm)); } while (0)
+#define arm_movkw(p, rd, imm, shift) do { g_assert ((shift) % 16 == 0); arm_format_mov ((p), 0x0, 0x3, (shift) / 16, (rd), (imm)); } while (0)
+
+/* PC-relative address calculation */
+#define arm_format_adrp(p, op, rd, target) do { guint64 imm1 = (guint64)(target); guint64 imm2 = (guint64)(p); int _imm = imm1 - imm2; arm_emit ((p), ((op) << 31) | (((_imm) & 0x3) << 29) | (0x10 << 24) | (((_imm >> 2) & 0x7ffff) << 5) | ((rd) << 0)); } while (0)
+
+#define arm_adrpx(p, rd, target) arm_format_adrp ((p), 0x1, (rd), (target))
+#define arm_adrx(p, rd, target) arm_format_adrp ((p), 0x0, (rd), (target))
+
+/* Bitfield move */
+#define arm_format_bfm(p, sf, opc, N, immr, imms, rn, rd) arm_emit ((p), ((sf) << 31) | ((opc) << 29) | (0x26 << 23) | ((N) << 22) | ((N) << 22) | ((immr) << 16) | ((imms) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_bfmx(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x1, 0x1, 0x1, (immr), (imms), (rn), (rd))
+#define arm_bfmw(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x0, 0x1, 0x0, (immr), (imms), (rn), (rd))
+#define arm_sbfmx(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x1, 0x0, 0x1, (immr), (imms), (rn), (rd))
+#define arm_sbfmw(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x0, 0x0, 0x0, (immr), (imms), (rn), (rd))
+#define arm_ubfmx(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x1, 0x2, 0x1, (immr), (imms), (rn), (rd))
+#define arm_ubfmw(p, rd, rn, immr, imms) arm_format_bfm ((p), 0x0, 0x2, 0x0, (immr), (imms), (rn), (rd))
+
+/* Sign extend and Zero-extend */
+#define arm_sxtbx(p, rd, rn) arm_sbfmx ((p), (rd), (rn), 0, 7)
+#define arm_sxtbw(p, rd, rn) arm_sbfmw ((p), (rd), (rn), 0, 7)
+#define arm_sxthx(p, rd, rn) arm_sbfmx ((p), (rd), (rn), 0, 15)
+#define arm_sxthw(p, rd, rn) arm_sbfmw ((p), (rd), (rn), 0, 15)
+#define arm_sxtwx(p, rd, rn) arm_sbfmx ((p), (rd), (rn), 0, 31)
+#define arm_uxtbx(p, rd, rn) arm_ubfmx ((p), (rd), (rn), 0, 7)
+#define arm_uxtbw(p, rd, rn) arm_ubfmw ((p), (rd), (rn), 0, 7)
+#define arm_uxthx(p, rd, rn) arm_ubfmx ((p), (rd), (rn), 0, 15)
+#define arm_uxthw(p, rd, rn) arm_ubfmw ((p), (rd), (rn), 0, 15)
+
+/* Extract register */
+#define arm_format_extr(p, sf, N, rd, rn, rm, imms) arm_emit ((p), ((sf) << 31) | (0x27 << 23) | ((N) << 22) | (0x0 << 21) | ((rm) << 16) | ((imms) << 10) | ((rn) << 5) | ((rd) << 0))
+#define arm_extrx(p, rd, rn, rm, lsb) arm_format_extr ((p), 0x1, 0x1, (rd), (rn), (rm), (lsb))
+#define arm_extrw(p, rd, rn, rm, lsb) arm_format_extr ((p), 0x0, 0x0, (rd), (rn), (rm), (lsb))
+
+/* Shift (immediate) */
+#define arm_asrx(p, rd, rn, shift) arm_sbfmx ((p), (rd), (rn), (shift), 63)
+#define arm_asrw(p, rd, rn, shift) arm_sbfmw ((p), (rd), (rn), (shift), 31)
+#define arm_lslx(p, rd, rn, shift) arm_ubfmx ((p), (rd), (rn), 64 - ((shift) % 64), 63 - ((shift) % 64))
+#define arm_lslw(p, rd, rn, shift) arm_ubfmw ((p), (rd), (rn), 32 - ((shift) % 32), 31 - ((shift) % 32))
+#define arm_lsrx(p, rd, rn, shift) arm_ubfmx ((p), (rd), (rn), shift, 63)
+#define arm_lsrw(p, rd, rn, shift) arm_ubfmw ((p), (rd), (rn), shift, 31)
+#define arm_rorx(p, rd, rs, shift) arm_extrx ((p), (rd), (rs), (rs), (shift))
+#define arm_rorw(p, rd, rs, shift) arm_extrw ((p), (rd), (rs), (rs), (shift))
+
+/* Arithmetic (shifted register) */
+#define arm_format_alu_shift(p, sf, op, S, rd, rn, rm, shift, imm6) arm_emit ((p), ((sf) << 31) | ((op) << 30) | ((S) << 29) | (0xb << 24) | ((shift) << 22) | (0x0 << 21) | ((rm) << 16) | ((imm6) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_addx_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x1, 0x0, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_addw_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x0, 0x0, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_addsx_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x1, 0x0, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_addsw_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x0, 0x0, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_subx_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x1, 0x1, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_subw_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x0, 0x1, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_subsx_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x1, 0x1, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_subsw_shift(p, rd, rn, rm, shift_type, amount) arm_format_alu_shift ((p), 0x0, 0x1, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_cmnx_shift(p, rn, rm, shift_type, amount) arm_addsx_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+#define arm_cmnw_shift(p, rn, rm, shift_type, amount) arm_addsw_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+#define arm_cmpx_shift(p, rn, rm, shift_type, amount) arm_subsx_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+#define arm_cmpw_shift(p, rn, rm, shift_type, amount) arm_subsw_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+#define arm_negx_shift(p, rd, rm, shift_type, amount) arm_subx_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+#define arm_negw_shift(p, rd, rm, shift_type, amount) arm_subw_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+#define arm_negsx_shift(p, rd, rm, shift_type, amount) arm_subsx_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+#define arm_negsw_shift(p, rd, rm, shift_type, amount) arm_subsw_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+
+#define arm_addx(p, rd, rn, rm) arm_addx_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_addw(p, rd, rn, rm) arm_addw_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_subx(p, rd, rn, rm) arm_subx_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_subw(p, rd, rn, rm) arm_subw_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_addsx(p, rd, rn, rm) arm_addsx_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_addsw(p, rd, rn, rm) arm_addsw_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_subsx(p, rd, rn, rm) arm_subsx_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_subsw(p, rd, rn, rm) arm_subsw_shift ((p), (rd), (rn), (rm), 0, 0)
+#define arm_cmpx(p, rd, rn) arm_cmpx_shift ((p), (rd), (rn), 0, 0)
+#define arm_cmpw(p, rd, rn) arm_cmpw_shift ((p), (rd), (rn), 0, 0)
+#define arm_negx(p, rd, rn) arm_negx_shift ((p), (rd), (rn), 0, 0)
+#define arm_negw(p, rd, rn) arm_negw_shift ((p), (rd), (rn), 0, 0)
+
+/* Arithmetic with carry */
+#define arm_format_adc(p, sf, op, S, rd, rn, rm) arm_emit ((p), ((sf) << 31) | ((op) << 30) | ((S) << 29) | (0xd0 << 21) | ((rm) << 16) | (0x0 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_adcx(p, rd, rn, rm) arm_format_adc ((p), 0x1, 0x0, 0x0, (rd), (rn), (rm))
+#define arm_adcw(p, rd, rn, rm) arm_format_adc ((p), 0x0, 0x0, 0x0, (rd), (rn), (rm))
+#define arm_adcsx(p, rd, rn, rm) arm_format_adc ((p), 0x1, 0x0, 0x1, (rd), (rn), (rm))
+#define arm_adcsw(p, rd, rn, rm) arm_format_adc ((p), 0x0, 0x0, 0x1, (rd), (rn), (rm))
+#define arm_sbcx(p, rd, rn, rm) arm_format_adc ((p), 0x1, 0x1, 0x0, (rd), (rn), (rm))
+#define arm_sbcw(p, rd, rn, rm) arm_format_adc ((p), 0x0, 0x1, 0x0, (rd), (rn), (rm))
+#define arm_sbcsx(p, rd, rn, rm) arm_format_adc ((p), 0x1, 0x1, 0x1, (rd), (rn), (rm))
+#define arm_sbcsw(p, rd, rn, rm) arm_format_adc ((p), 0x0, 0x1, 0x1, (rd), (rn), (rm))
+#define arm_ngcx(p, rd, rm) arm_sbcx ((p), (rd), ARMREG_RZR, (rm))
+#define arm_ngcw(p, rd, rm) arm_sbcw ((p), (rd), ARMREG_RZR, (rm))
+#define arm_ngcsx(p, rd, rm) arm_sbcsx ((p), (rd), ARMREG_RZR, (rm))
+#define arm_ngcsw(p, rd, rm) arm_sbcsw ((p), (rd), ARMREG_RZR, (rm))
+
+/* Logical (shifted register) */
+#define arm_format_logical_shift(p, sf, op, N, rd, rn, rm, shift, imm6) arm_emit ((p), ((sf) << 31) | ((op) << 29) | (0xa << 24) | ((shift) << 22) | ((N) << 21) | ((rm) << 16) | ((imm6) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_andx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x0, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_andw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x0, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_andsx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x3, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_andsw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x3, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_bicx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x0, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_bicw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x0, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_bicsx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x3, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_bicsw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x3, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_eonx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x2, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_eonw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x2, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_eorx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x2, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_eorw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x2, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_orrx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x1, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_orrw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x1, 0x0, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_ornx_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x1, 0x1, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_ornw_shift(p, rd, rn, rm, shift_type, amount) arm_format_logical_shift ((p), 0x0, 0x1, 0x1, (rd), (rn), (rm), (shift_type), (amount))
+#define arm_mvnx_shift(p, rd, rm, shift_type, amount) arm_ornx_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+#define arm_mvnw_shift(p, rd, rm, shift_type, amount) arm_ornw_shift ((p), (rd), ARMREG_RZR, (rm), (shift_type), (amount))
+#define arm_tstx_shift(p, rn, rm, shift_type, amount) arm_andsx_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+#define arm_tstw_shift(p, rn, rm, shift_type, amount) arm_andsw_shift ((p), ARMREG_RZR, (rn), (rm), (shift_type), (amount))
+/* Aliases */
+#define arm_andx(p, rd, rn, rm) arm_andx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_andw(p, rd, rn, rm) arm_andw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_andsx(p, rd, rn, rm) arm_andsx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_andsw(p, rd, rn, rm) arm_andsw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_bixx(p, rd, rn, rm) arm_bixx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_bixw(p, rd, rn, rm) arm_bixw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_bixsx(p, rd, rn, rm) arm_bixsx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_bixsw(p, rd, rn, rm) arm_bixsw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_eonx(p, rd, rn, rm) arm_eonx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_eonw(p, rd, rn, rm) arm_eonw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_eorx(p, rd, rn, rm) arm_eorx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_eorw(p, rd, rn, rm) arm_eorw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_orrx(p, rd, rn, rm) arm_orrx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_orrw(p, rd, rn, rm) arm_orrw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_ornx(p, rd, rn, rm) arm_ornx_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_ornw(p, rd, rn, rm) arm_ornw_shift(p, rd, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_mvnx(p, rd, rm) arm_mvnx_shift(p, rd, rm, ARMSHIFT_LSL, 0)
+#define arm_mvnw(p, rd, rm) arm_mvnw_shift(p, rd, rm, ARMSHIFT_LSL, 0)
+#define arm_tstx(p, rn, rm) arm_tstx_shift(p, rn, rm, ARMSHIFT_LSL, 0)
+#define arm_tstw(p, rn, rm) arm_tstw_shift(p, rn, rm, ARMSHIFT_LSL, 0)
+
+/* Move (register) */
+#define arm_movx(p, rn, rm) arm_orrx_shift ((p), (rn), ARMREG_RZR, (rm), ARMSHIFT_LSL, 0)
+#define arm_movw(p, rn, rm) arm_orrw_shift ((p), (rn), ARMREG_RZR, (rm), ARMSHIFT_LSL, 0)
+
+/* Not an official alias */
+#define arm_movspx(p, rn, rm) arm_addx_imm ((p), (rn), (rm), 0)
+
+/* Shift (register) */
+#define arm_format_shift_reg(p, sf, op2, rd, rn, rm) arm_emit ((p), ((sf) << 31) | (0xd6 << 21) | ((rm) << 16) | (0x2 << 12) | ((op2) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_asrvx(p, rd, rn, rm) arm_format_shift_reg ((p), 0x1, 0x2, (rd), (rn), (rm))
+#define arm_asrvw(p, rd, rn, rm) arm_format_shift_reg ((p), 0x0, 0x2, (rd), (rn), (rm))
+#define arm_lslvx(p, rd, rn, rm) arm_format_shift_reg ((p), 0x1, 0x0, (rd), (rn), (rm))
+#define arm_lslvw(p, rd, rn, rm) arm_format_shift_reg ((p), 0x0, 0x0, (rd), (rn), (rm))
+#define arm_lsrvx(p, rd, rn, rm) arm_format_shift_reg ((p), 0x1, 0x1, (rd), (rn), (rm))
+#define arm_lsrvw(p, rd, rn, rm) arm_format_shift_reg ((p), 0x0, 0x1, (rd), (rn), (rm))
+#define arm_rorvx(p, rd, rn, rm) arm_format_shift_reg ((p), 0x1, 0x3, (rd), (rn), (rm))
+#define arm_rorvw(p, rd, rn, rm) arm_format_shift_reg ((p), 0x0, 0x3, (rd), (rn), (rm))
+
+/* Multiply */
+#define arm_format_mul(p, sf, o0, rd, rn, rm, ra) arm_emit ((p), ((sf) << 31) | (0x0 << 29) | (0x1b << 24) | (0x0 << 21) | ((rm) << 16) | ((o0) << 15) | ((ra) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_maddx(p, rd, rn, rm, ra) arm_format_mul((p), 0x1, 0x0, (rd), (rn), (rm), (ra))
+#define arm_maddw(p, rd, rn, rm, ra) arm_format_mul((p), 0x0, 0x0, (rd), (rn), (rm), (ra))
+#define arm_msubx(p, rd, rn, rm, ra) arm_format_mul((p), 0x1, 0x1, (rd), (rn), (rm), (ra))
+#define arm_msubw(p, rd, rn, rm, ra) arm_format_mul((p), 0x0, 0x1, (rd), (rn), (rm), (ra))
+#define arm_mnegx(p, rd, rn, rm) arm_msubx ((p), (rd), (rn), (rm), ARMREG_RZR)
+#define arm_mnegw(p, rd, rn, rm) arm_msubw ((p), (rd), (rn), (rm), ARMREG_RZR)
+#define arm_mulx(p, rd, rn, rm) arm_maddx ((p), (rd), (rn), (rm), ARMREG_RZR)
+#define arm_mulw(p, rd, rn, rm) arm_maddw ((p), (rd), (rn), (rm), ARMREG_RZR)
+
+/* FIXME: Missing multiple opcodes */
+
+/* Division */
+#define arm_format_div(p, sf, o1, rd, rn, rm) arm_emit ((p), ((sf) << 31) | (0xd6 << 21) | ((rm) << 16) | (0x1 << 11) | ((o1) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_sdivx(p, rd, rn, rm) arm_format_div ((p), 0x1, 0x1, (rd), (rn), (rm))
+#define arm_sdivw(p, rd, rn, rm) arm_format_div ((p), 0x0, 0x1, (rd), (rn), (rm))
+#define arm_udivx(p, rd, rn, rm) arm_format_div ((p), 0x1, 0x0, (rd), (rn), (rm))
+#define arm_udivw(p, rd, rn, rm) arm_format_div ((p), 0x0, 0x0, (rd), (rn), (rm))
+
+/* Conditional select */
+#define arm_format_csel(p, sf, op, op2, cond, rd, rn, rm) arm_emit ((p), ((sf) << 31) | ((op) << 30) | (0xd4 << 21) | ((rm) << 16) | ((cond) << 12) | ((op2) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_cselx(p, cond, rd, rn, rm) arm_format_csel ((p), 0x1, 0x0, 0x0, (cond), (rd), (rn), (rm))
+#define arm_cselw(p, cond, rd, rn, rm) arm_format_csel ((p), 0x0, 0x0, 0x0, (cond), (rd), (rn), (rm))
+#define arm_csincx(p, cond, rd, rn, rm) arm_format_csel ((p), 0x1, 0x0, 0x1, (cond), (rd), (rn), (rm))
+#define arm_csincw(p, cond, rd, rn, rm) arm_format_csel ((p), 0x0, 0x0, 0x1, (cond), (rd), (rn), (rm))
+#define arm_csinvx(p, cond, rd, rn, rm) arm_format_csel ((p), 0x1, 0x1, 0x0, (cond), (rd), (rn), (rm))
+#define arm_csinvw(p, cond, rd, rn, rm) arm_format_csel ((p), 0x0, 0x1, 0x0, (cond), (rd), (rn), (rm))
+#define arm_csnegx(p, cond, rd, rn, rm) arm_format_csel ((p), 0x1, 0x1, 0x1, (cond), (rd), (rn), (rm))
+#define arm_csnegw(p, cond, rd, rn, rm) arm_format_csel ((p), 0x0, 0x1, 0x1, (cond), (rd), (rn), (rm))
+
+#define arm_cset(p, cond, rd) arm_csincx ((p), ((cond) ^ 0x1), (rd), ARMREG_RZR, ARMREG_RZR)
+
+/* C5.6.68 (HINT) */
+#define arm_hint(p, imm) arm_emit ((p), (0xd5032 << 12) | ((imm) << 5) | (0x1f << 0))
+#define arm_nop(p) arm_hint ((p), 0x0)
+
+/* C5.6.29 BRK */
+#define arm_brk(p, imm) arm_emit ((p), (0xd4 << 24) | (0x1 << 21) | ((imm) << 5))
+
+/* C6.3.114 FMOV (General) */
+#define arm_format_fmov_gr(p, sf, type, rmode, opcode, rn, rd) arm_emit ((p), ((sf) << 31) | (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rmode) << 19) | ((opcode) << 16) | ((rn) << 5) | ((rd) << 0))
+
+/* Move gr->vfp */
+#define arm_fmov_rx_to_double(p, dd, xn) arm_format_fmov_gr ((p), 0x1, 0x1, 0x0, 0x7, (xn), (dd))
+
+/* Move vfp->gr */
+#define arm_fmov_double_to_rx(p, xd, dn) arm_format_fmov_gr ((p), 0x1, 0x1, 0x0, 0x6, (dn), (xd))
+
+/* C6.3.113 FMOV (register) */
+#define arm_format_fmov(p, type, rn, rd) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | (0x10 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fmovd(p, dd, dn) arm_format_fmov ((p), 0x1, (dn), (dd))
+#define arm_fmovs(p, dd, dn) arm_format_fmov ((p), 0x0, (dn), (dd))
+
+/* C6.3.54 FCMP */
+#define arm_format_fcmp(p, type, opc, rn, rm) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rm) << 16) | (0x8 << 10) | ((rn) << 5) | ((opc) << 3))
+
+#define arm_fcmpd(p, dn, dm) arm_format_fcmp (p, 0x1, 0x0, (dn), (dm))
+#define arm_fcmps(p, dn, dm) arm_format_fcmp (p, 0x0, 0x0, (dn), (dm))
+
+/* Float precision */
+#define arm_format_fcvt(p, type, opc, rn, rd) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | (0x1 << 17) | ((opc) << 15) | (0x10 << 10) | ((rn) << 5) | ((rd) << 0))
+
+/* C6.3.57 FCVT */
+/* single->double */
+#define arm_fcvt_sd(p, dd, sn) arm_format_fcvt ((p), 0x0, 0x1, (sn), (dd))
+/* double->single */
+#define arm_fcvt_ds(p, sd, dn) arm_format_fcvt ((p), 0x1, 0x0, (dn), (sd))
+
+/* Float conversion to integer conversion */
+#define arm_format_fcvtz(p, sf, type, rmode, opcode, rn, rd) arm_emit ((p), ((sf) << 31) | (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rmode) << 19) | ((opcode) << 16) | ((rn) << 5) | ((rd) << 0))
+
+/* C6.3.80 FCVTZS (scalar, integer) */
+#define arm_fcvtzs_dw(p, rd, rn) arm_format_fcvtz ((p), 0x0, 0x1, 0x3, 0x0, (rn), (rd))
+#define arm_fcvtzs_dx(p, rd, rn) arm_format_fcvtz ((p), 0x1, 0x1, 0x3, 0x0, (rn), (rd))
+#define arm_fcvtzs_sw(p, rd, rn) arm_format_fcvtz ((p), 0x0, 0x0, 0x3, 0x0, (rn), (rd))
+#define arm_fcvtzs_sx(p, rd, rn) arm_format_fcvtz ((p), 0x1, 0x0, 0x3, 0x0, (rn), (rd))
+
+/* C6.3.84 FCVTZU (scalar, integer) */
+#define arm_fcvtzu_dw(p, rd, rn) arm_format_fcvtz ((p), 0x0, 0x1, 0x3, 0x1, (rn), (rd))
+#define arm_fcvtzu_dx(p, rd, rn) arm_format_fcvtz ((p), 0x1, 0x1, 0x3, 0x1, (rn), (rd))
+#define arm_fcvtzu_sw(p, rd, rn) arm_format_fcvtz ((p), 0x0, 0x0, 0x3, 0x1, (rn), (rd))
+#define arm_fcvtzu_sx(p, rd, rn) arm_format_fcvtz ((p), 0x1, 0x0, 0x3, 0x1, (rn), (rd))
+
+/* C6.3.208 SCVTF (vector, integer) */
+#define arm_format_scvtf_vector(p, sz, rn, rd) arm_emit ((p), (0x1 << 30) | (0x0 << 29) | (0x1e << 24) | ((sz) << 22) | (0x10 << 17) | (0x1d << 12) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_scvtf_d(p, dd, dn) arm_format_scvtf_vector ((p), 0x1, (dn), (dd))
+#define arm_scvtf_s(p, sd, sn) arm_format_scvtf_vector ((p), 0x0, (sn), (sd))
+
+/* C6.3.210 SCVTF (scalar, integer) */
+#define arm_format_scvtf_scalar(p, sf, type, rn, rd) arm_emit ((p), ((sf) << 31) | (0x1e << 24) | ((type) << 22) | (0x1 << 21) | (0x2 << 16) | (0x0 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_scvtf_rx_to_d(p, dd, rn) arm_format_scvtf_scalar ((p), 0x1, 0x1, rn, dd)
+#define arm_scvtf_rw_to_d(p, dd, rn) arm_format_scvtf_scalar ((p), 0x0, 0x1, rn, dd)
+#define arm_scvtf_rx_to_s(p, dd, rn) arm_format_scvtf_scalar ((p), 0x1, 0x0, rn, dd)
+#define arm_scvtf_rw_to_s(p, dd, rn) arm_format_scvtf_scalar ((p), 0x0, 0x0, rn, dd)
+
+/* C6.3.306 UCVTF (vector, integer) */
+#define arm_format_ucvtf_vector(p, sz, rn, rd) arm_emit ((p), (0x1 << 30) | (0x1 << 29) | (0x1e << 24) | ((sz) << 22) | (0x10 << 17) | (0x1d << 12) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_ucvtf_d(p, dd, dn) arm_format_ucvtf_vector ((p), 0x1, (dn), (dd))
+#define arm_ucvtf_s(p, sd, sn) arm_format_ucvtf_vector ((p), 0x0, (sn), (sd))
+
+/* C6.3.308 UCVTF (scalar, integer) */
+#define arm_format_ucvtf_scalar(p, sf, type, rn, rd) arm_emit ((p), ((sf) << 31) | (0x1e << 24) | ((type) << 22) | (0x1 << 21) | (0x3 << 16) | (0x0 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_ucvtf_rx_to_d(p, dd, rn) arm_format_ucvtf_scalar ((p), 0x1, 0x1, rn, dd)
+#define arm_ucvtf_rw_to_d(p, dd, rn) arm_format_ucvtf_scalar ((p), 0x0, 0x1, rn, dd)
+
+/* C6.3.41 FADD (scalar) */
+#define arm_format_fadd_scalar(p, type, rd, rn, rm) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rm) << 16) | (0x1 << 13) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fadd_d(p, rd, rn, rm) arm_format_fadd_scalar ((p), 0x1, (rd), (rn), (rm))
+#define arm_fadd_s(p, rd, rn, rm) arm_format_fadd_scalar ((p), 0x0, (rd), (rn), (rm))
+
+/* C6.3.149 FSUB (scalar) */
+#define arm_format_fsub_scalar(p, type, rd, rn, rm) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rm) << 16) | (0x1 << 13) | (0x1 << 12) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fsub_d(p, rd, rn, rm) arm_format_fsub_scalar ((p), 0x1, (rd), (rn), (rm))
+#define arm_fsub_s(p, rd, rn, rm) arm_format_fsub_scalar ((p), 0x0, (rd), (rn), (rm))
+
+/* C6.3.119 FMUL (scalar) */
+#define arm_format_fmul_scalar(p, type, rd, rn, rm) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rm) << 16) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fmul_d(p, rd, rn, rm) arm_format_fmul_scalar ((p), 0x1, (rd), (rn), (rm))
+#define arm_fmul_s(p, rd, rn, rm) arm_format_fmul_scalar ((p), 0x0, (rd), (rn), (rm))
+
+/* C6.3.86 FDIV (scalar) */
+#define arm_format_fdiv_scalar(p, type, rd, rn, rm) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((rm) << 16) | (0x1 << 12) | (0x2 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fdiv_d(p, rd, rn, rm) arm_format_fdiv_scalar ((p), 0x1, (rd), (rn), (rm))
+#define arm_fdiv_s(p, rd, rn, rm) arm_format_fdiv_scalar ((p), 0x0, (rd), (rn), (rm))
+
+/* C6.3.116 FMSUB */
+#define arm_format_fmsub(p, type, rd, rn, rm, ra) arm_emit ((p), (0x1f << 24) | ((type) << 22) | (0x0 << 21) | ((rm) << 16) | (0x1 << 15) | ((ra) << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fmsub_d(p, rd, rn, rm, ra) arm_format_fmsub ((p), 0x1, (rd), (rn), (rm), (ra))
+
+/* C6.3.123 FNEG */
+#define arm_format_fneg(p, type, rd, rn) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | (0x2 << 15) | (0x10 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fneg_d(p, rd, rn) arm_format_fneg ((p), 0x1, (rd), (rn))
+#define arm_fneg_s(p, rd, rn) arm_format_fneg ((p), 0x0, (rd), (rn))
+
+/* C6.3.37 FABS (scalar) */
+#define arm_format_fabs(p, type, opc, rd, rn) arm_emit ((p), (0x1e << 24) | ((type) << 22) | (0x1 << 21) | ((opc) << 15) | (0x10 << 10) | ((rn) << 5) | ((rd) << 0))
+
+#define arm_fabs_d(p, rd, rn) arm_format_fabs ((p), 0x1, 0x1, (rd), (rn))
+
+/* C5.6.60 DMB */
+#define arm_format_dmb(p, opc, CRm) arm_emit ((p), (0x354 << 22) | (0x3 << 16) | (0x3 << 12) | ((CRm) << 8) | (0x1 << 7) | ((opc) << 5) | (0x1f << 0))
+
+#define ARM_DMB_LD 0x1
+#define ARM_DMB_ST 0x2
+#define ARM_DMB_ALL 0x3
+#define ARM_DMB_SY 0xc
+
+#define arm_dmb(p, imm) arm_format_dmb ((p), 0x1, (imm))
+
+/* C5.6.129 MRS */
+
+#define ARM_MRS_REG_TPIDR_EL0 0x5e82
+
+#define arm_format_mrs(p, sysreg, rt) arm_emit ((p), (0x354 << 22) | (0x1 << 21) | (0x1 << 20) | ((sysreg) << 5) | ((rt) << 0))
+
+#define arm_mrs(p, rt, sysreg) arm_format_mrs ((p), (sysreg), (rt))
+
+#endif /* __arm_CODEGEN_H__ */
index 1dbd1c6e279d40613c8d7ccf9eb3ea0664528993..c579c88a9b3a990a26afc0edaeac0c2da8693417 100644 (file)
@@ -4,6 +4,7 @@
  * Copyright (c) 2004 Novell, Inc
  * Author: Paolo Molaro (lupus@ximian.com)
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /* registers */
index d4d25a254f980587bae505a5fd4deefa6d6a4749..869365b4bccd9b3d93d99dd1184dfbc049253d8f 100644 (file)
@@ -8,6 +8,7 @@
    Copyright (C)  2007-2008 Andreas Faerber
 
    for testing do the following: ./test | as -o test.o
+   Licensed under the MIT license. See LICENSE file in the project root for full license information.
 */
 
 #ifndef __MONO_PPC_CODEGEN_H__
index 4c3cd243520ea41e3330a8f5bb811b8bd03ff736..97db6ce6eb9a711c5a3da86e2c7c668630d85594 100644 (file)
@@ -1,5 +1,6 @@
 /*
    Copyright (C)  2001 Radek Doulik
+   * Licensed under the MIT license. See LICENSE file in the project root for full license information.
 */
 
 #ifndef S390X_H
index ff3fe325a791983f0d28784154b7149543e877bd..6c9d63f37e991fc8cbaeedf8ce4fd635695253c3 100644 (file)
@@ -10,6 +10,7 @@
  * 
  * Copyright (C)  2000 Intel Corporation.  All rights reserved.
  * Copyright (C)  2001, 2002 Ximian, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef X86_H
index 3d6cd252366431fc9f6cb255f0aba34499c556c0..eb0f168850aefc9a73ace127cef519640ae8c284 100755 (executable)
@@ -6,6 +6,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright (C) 2005 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <glib.h>
index fd9a5cb36155c7108d6c49e6aed09948e711ff3c..a0e621f7cb0b47e6adfb71e310cd19b1fecd8295 100644 (file)
@@ -6,6 +6,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright (C) 2005 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONODIS_DECLSEC_H__
index 24df084d6e39865c3f8aaafcbd5a3467fd9cadae..f3724e4384debca76a5eae810a91e4dc8333e278 100755 (executable)
@@ -6,6 +6,7 @@
  *
  * (C) 2001 Ximian, Inc.
  * Copyright 2012 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
index d8f6f8558fa8d30927b50760ab82e6715e09d60c..d1b85c5509abb7c864ff51ac4b92202f38dc5475 100644 (file)
@@ -11,6 +11,7 @@
  *   Structs are not being labeled as `valuetype' classes
  *   
  *   How are fields with literals mapped to constants?
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
index 3cb0a73d5785d8941318152625124b807ee374c8..f31d6cbfb4e1d984b52e866c5c3b5970c370d112 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002-2011 Novell, Inc.
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 8838c304e9c35577a0eaed9f9bf4f12c79adcdab..282cbe93a29b8e6f60923db0fafba329529ac924 100644 (file)
@@ -6,6 +6,7 @@
  *     Dick Porter (dick@ximian.com)
  *
  * Copyright (c) 2006 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 8beb367f2e638097cd9f3c6d1c5817b49f1fadc7..d7e9dba666dcfe3bfdb97774be8a0a9d5e994c21 100644 (file)
@@ -6,6 +6,7 @@
  *     Dick Porter (dick@ximian.com)
  *
  * Copyright (C) 2006 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _WAPI_IO_PORTABILITY_H_
index fad582754fda1e8d96a76f40d0718df6a1fc91f4..9af4b1f0a11f0c4d65152b1b5ab7eccdc75b3168 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _WAPI_IO_PRIVATE_H_
index 51f60f453343b5bb14bd6848ba3580ec1f533cf4..f67ff65f842d42f6ab847bf40d867d4f49dce97c 100644 (file)
@@ -5,6 +5,7 @@
  *  Marek Habersack <grendel@twistedcode.net>
  *
  * Copyright 2016 Xamarin, Inc (http://xamarin.com/)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __IO_TRACE_H
index b751134d7045aa6a2cae4e3fc3ba186fedbd66c1..24ec5baffb37370c346d81591ceaae514aac1845 100644 (file)
@@ -7,6 +7,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright (c) 2002-2006 Novell, Inc.
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com).
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -989,7 +990,14 @@ static gboolean file_setfiletime(gpointer handle,
                        SetLastError (ERROR_INVALID_PARAMETER);
                        return(FALSE);
                }
-               
+
+               if (sizeof (utbuf.actime) == 4 && ((access_ticks - 116444736000000000ULL) / 10000000) > INT_MAX) {
+                       MONO_TRACE (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: attempt to set write time that is too big for a 32bits time_t",
+                                  __func__);
+                       SetLastError (ERROR_INVALID_PARAMETER);
+                       return(FALSE);
+               }
+
                utbuf.actime=(access_ticks - 116444736000000000ULL) / 10000000;
        } else {
                utbuf.actime=statbuf.st_atime;
@@ -1007,6 +1015,12 @@ static gboolean file_setfiletime(gpointer handle,
                        SetLastError (ERROR_INVALID_PARAMETER);
                        return(FALSE);
                }
+               if (sizeof (utbuf.modtime) == 4 && ((write_ticks - 116444736000000000ULL) / 10000000) > INT_MAX) {
+                       MONO_TRACE (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: attempt to set write time that is too big for a 32bits time_t",
+                                  __func__);
+                       SetLastError (ERROR_INVALID_PARAMETER);
+                       return(FALSE);
+               }
                
                utbuf.modtime=(write_ticks - 116444736000000000ULL) / 10000000;
        } else {
index 305c0ab48527cb7fd053c050a04041e7c1d7b10c..c014a2d3dc4f983c19f4b70dcb878fa47ef0f751 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright (c) 2002-2009 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
index 3cd41f67fe33d045e7d9ede7e033f40b35b407f9..2856d4fcd615cf7dbb973f27830bc391c66255df 100644 (file)
@@ -7,6 +7,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright (c) 2002-2009 Novell, Inc.
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 5a9e91b4831593d9eec1f00d6d7f1b39e9bac91b..913f0b8af4b43604a528192492512caff7fac786 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002-2011 Novell, Inc.
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -1286,7 +1287,8 @@ GetExitCodeProcess (gpointer process, guint32 *code)
                        *code = STILL_ACTIVE;
                        return TRUE;
                } else {
-                       return FALSE;
+                       *code = -1;
+                       return TRUE;
                }
        }
 
index bb65b5f799cd44f8279b4419777e5a16210f6aa9..304fd35adf807e349c77529ee2813686d0e6553a 100644 (file)
@@ -7,6 +7,7 @@
  * (C) 2002-2006 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index cb0fb34bf953e559f4d66acea259b39b407cfc1a..3f61191b3146cbdf38a3cac5aabd935bc63152ae 100644 (file)
@@ -1,5 +1,6 @@
 /*
  * Copyright 2014 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_METADATA_ABI_DETAILS_H__
 #define __MONO_METADATA_ABI_DETAILS_H__
index 6ffc0a3f2af47ac0276940aa3295cee7b9713751..effa46abdd1d93de67209e08d95a85a33301d450 100644 (file)
@@ -9,6 +9,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2012 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #undef ASSEMBLY_LOAD_DEBUG
 #include <config.h>
@@ -80,7 +81,7 @@
  * Changes which are already detected at runtime, like the addition
  * of icalls, do not require an increment.
  */
-#define MONO_CORLIB_VERSION 143
+#define MONO_CORLIB_VERSION 146
 
 typedef struct
 {
@@ -257,7 +258,6 @@ mono_runtime_init_checked (MonoDomain *domain, MonoThreadStartCB start_cb, MonoT
        mono_install_assembly_postload_search_hook ((MonoAssemblySearchFunc)mono_domain_assembly_postload_search, GUINT_TO_POINTER (FALSE));
        mono_install_assembly_postload_refonly_search_hook ((MonoAssemblySearchFunc)mono_domain_assembly_postload_search, GUINT_TO_POINTER (TRUE));
        mono_install_assembly_load_hook (mono_domain_fire_assembly_load, NULL);
-       mono_install_lookup_dynamic_token (mono_reflection_lookup_dynamic_token);
 
        mono_thread_init (start_cb, attach_cb);
 
@@ -320,7 +320,7 @@ mono_get_corlib_version (void)
        if (! (field->type->attrs & FIELD_ATTRIBUTE_STATIC))
                return -1;
        value = mono_field_get_value_object_checked (mono_domain_get (), field, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_assert_ok (&error);
        return *(gint32*)((gchar*)value + sizeof (MonoObject));
 }
 
@@ -435,13 +435,18 @@ mono_domain_create_appdomain (char *friendly_name, char *configuration_file)
 
        klass = mono_class_load_from_name (mono_defaults.corlib, "System", "AppDomainSetup");
        setup = (MonoAppDomainSetup *) mono_object_new_checked (mono_domain_get (), klass, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error))
+               goto fail;
        setup->configuration_file = configuration_file != NULL ? mono_string_new (mono_domain_get (), configuration_file) : NULL;
 
        ad = mono_domain_create_appdomain_internal (friendly_name, setup, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error))
+               goto fail;
 
        return mono_domain_from_appdomain (ad);
+fail:
+       mono_error_cleanup (&error);
+       return NULL;
 }
 
 /**
@@ -938,23 +943,20 @@ mono_domain_set_options_from_config (MonoDomain *domain)
 MonoAppDomain *
 ves_icall_System_AppDomain_createDomain (MonoString *friendly_name, MonoAppDomainSetup *setup)
 {
+       MonoError error;
+       MonoAppDomain *ad = NULL;
 #ifdef DISABLE_APPDOMAINS
-       mono_set_pending_exception (mono_get_exception_not_supported ("AppDomain creation is not supported on this runtime."));
-       return NULL;
+       mono_error_set_not_supported (&error, "AppDomain creation is not supported on this runtime.");
 #else
-       MonoError error;
        char *fname;
-       MonoAppDomain *ad;
 
        fname = mono_string_to_utf8 (friendly_name);
        ad = mono_domain_create_appdomain_internal (fname, setup, &error);
 
        g_free (fname);
-
-       mono_error_raise_exception (&error);
-
-       return ad;
 #endif
+       mono_error_set_pending_exception (&error);
+       return ad;
 }
 
 MonoArray *
@@ -987,7 +989,9 @@ ves_icall_System_AppDomain_GetAssemblies (MonoAppDomain *ad, MonoBoolean refonly
        }
        mono_domain_assemblies_unlock (domain);
 
-       res = mono_array_new (domain, mono_class_get_assembly_class (), assemblies->len);
+       res = mono_array_new_checked (domain, mono_class_get_assembly_class (), assemblies->len, &error);
+       if (!is_ok (&error))
+               goto leave;
        for (i = 0; i < assemblies->len; ++i) {
                ass = (MonoAssembly *)g_ptr_array_index (assemblies, i);
                MonoReflectionAssembly *ass_obj = mono_assembly_get_object_checked (domain, ass, &error);
@@ -1057,18 +1061,13 @@ mono_domain_assembly_postload_search (MonoAssemblyName *aname, MonoAssembly *req
 
        /* FIXME: We invoke managed code here, so there is a potential for deadlocks */
        str = mono_string_new (domain, aname_str);
+       g_free (aname_str);
        if (!str) {
-               g_free (aname_str);
                return NULL;
        }
 
        assembly = mono_try_assembly_resolve (domain, str, requesting, refonly, &error);
-       if (!mono_error_ok (&error)) {
-               g_free (aname_str);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
-       }
-
-       g_free (aname_str);
+       mono_error_cleanup (&error);
 
        if (assembly)
                return assembly->assembly;
@@ -1163,7 +1162,7 @@ mono_domain_fire_assembly_load (MonoAssembly *assembly, gpointer user_data)
        *params = ref_assembly;
 
        mono_runtime_invoke_checked (assembly_load_method, domain->domain, params, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_cleanup (&error);
 }
 
 /*
@@ -1766,7 +1765,7 @@ mono_make_shadow_copy (const char *filename, MonoError *oerror)
        if (!mono_error_ok (&error)) {
                mono_error_cleanup (&error);
                g_free (dir_name);
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy (invalid characters in shadow directory name).");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy (invalid characters in shadow directory name).");
                return NULL;
        }
 
@@ -1781,13 +1780,13 @@ mono_make_shadow_copy (const char *filename, MonoError *oerror)
        shadow = get_shadow_assembly_location (filename, &error);
        if (!mono_error_ok (&error)) {
                mono_error_cleanup (&error);
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy (invalid characters in file name).");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy (invalid characters in file name).");
                return NULL;
        }
 
        if (ensure_directory_exists (shadow) == FALSE) {
                g_free (shadow);
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy (ensure directory exists).");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy (ensure directory exists).");
                return NULL;
        }       
 
@@ -1824,7 +1823,7 @@ mono_make_shadow_copy (const char *filename, MonoError *oerror)
                if (GetLastError() == ERROR_FILE_NOT_FOUND || GetLastError() == ERROR_PATH_NOT_FOUND)
                        return NULL; /* file not found, shadow copy failed */
 
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy (CopyFile).");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy (CopyFile).");
                return NULL;
        }
 
@@ -1843,14 +1842,14 @@ mono_make_shadow_copy (const char *filename, MonoError *oerror)
        
        if (copy_result == FALSE)  {
                g_free (shadow);
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy of sibling data (CopyFile).");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy of sibling data (CopyFile).");
                return NULL;
        }
 
        /* Create a .ini file containing the original assembly location */
        if (!shadow_copy_create_ini (shadow, filename)) {
                g_free (shadow);
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Failed to create shadow copy .ini file.");
+               mono_error_set_execution_engine (oerror, "Failed to create shadow copy .ini file.");
                return NULL;
        }
 
@@ -2146,10 +2145,11 @@ ves_icall_System_AppDomain_LoadAssembly (MonoAppDomain *ad,  MonoString *assRef,
 void
 ves_icall_System_AppDomain_InternalUnload (gint32 domain_id)
 {
+       MonoException *exc = NULL;
        MonoDomain * domain = mono_domain_get_by_id (domain_id);
 
        if (NULL == domain) {
-               MonoException *exc = mono_get_exception_execution_engine ("Failed to unload domain, domain id not found");
+               mono_get_exception_execution_engine ("Failed to unload domain, domain id not found");
                mono_set_pending_exception (exc);
                return;
        }
@@ -2169,7 +2169,9 @@ ves_icall_System_AppDomain_InternalUnload (gint32 domain_id)
        return;
 #endif
 
-       mono_domain_unload (domain);
+       mono_domain_try_unload (domain, (MonoObject**)&exc);
+       if (exc)
+               mono_set_pending_exception (exc);
 }
 
 gboolean
@@ -2206,8 +2208,10 @@ ves_icall_System_AppDomain_ExecuteAssembly (MonoAppDomain *ad,
        if (!method)
                g_error ("No entry point method found in %s due to %s", image->name, mono_error_get_message (&error));
 
-       if (!args)
-               args = (MonoArray *) mono_array_new (ad->data, mono_defaults.string_class, 0);
+       if (!args) {
+               args = (MonoArray *) mono_array_new_checked (ad->data, mono_defaults.string_class, 0, &error);
+               mono_error_assert_ok (&error);
+       }
 
        return mono_runtime_exec_main (method, (MonoArray *)args, NULL);
 }
@@ -2306,7 +2310,7 @@ ves_icall_System_AppDomain_InternalGetProcessGuid (MonoString* newguid)
                MonoError error;
                MonoString *res = NULL;
                res = mono_string_new_utf16_checked (mono_domain_get (), process_guid, sizeof(process_guid)/2, &error);
-               mono_error_raise_exception (&error);
+               mono_error_set_pending_exception (&error);
                return res;
        }
        memcpy (process_guid, mono_string_chars(newguid), sizeof(process_guid));
@@ -2427,7 +2431,17 @@ unload_thread_main (void *arg)
        /* Have to attach to the runtime so shutdown can wait for this thread */
        /* Force it to be attached to avoid racing during shutdown. */
        thread = mono_thread_attach_full (mono_get_root_domain (), TRUE, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error)) {
+               data->failure_reason = g_strdup (mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+               goto failure;
+       }
+       mono_thread_set_name_internal (thread->internal_thread, mono_string_new (mono_get_root_domain (), "Domain unloader"), TRUE, &error);
+       if (!is_ok (&error)) {
+               data->failure_reason = g_strdup (mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+               goto failure;
+       }
 
        /* 
         * FIXME: Abort our parent thread last, so we can return a failure 
@@ -2516,8 +2530,6 @@ mono_domain_unload (MonoDomain *domain)
 {
        MonoObject *exc = NULL;
        mono_domain_try_unload (domain, &exc);
-       if (exc)
-               mono_raise_exception ((MonoException*)exc);
 }
 
 static guint32
index 58313a937eb4c9007f07fa78c63babf1d63d5c39..ebf94234bb21b83ac59f44a776c2bc2e5d2aff47 100644 (file)
@@ -89,6 +89,7 @@ mono_domain_set            (MonoDomain *domain, mono_bool force);
 MONO_API void
 mono_domain_set_internal   (MonoDomain *domain);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API void
 mono_domain_unload (MonoDomain *domain);
 
index 275bcbb234309c1498d30ac3a283022c84b8a951..7f2b5fdb6a62e11741c63c09f4ba5098835219de 100644 (file)
@@ -7,6 +7,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
@@ -1635,7 +1636,14 @@ mono_assembly_open_full (const char *filename, MonoImageOpenStatus *status, gboo
        if (!mono_assembly_is_in_gac (fname)) {
                MonoError error;
                new_fname = mono_make_shadow_copy (fname, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               if (!is_ok (&error)) {
+                       mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_ASSEMBLY,
+                                   "Assembly Loader shadow copy error: %s.", mono_error_get_message (&error));
+                       mono_error_cleanup (&error);
+                       *status = MONO_IMAGE_IMAGE_INVALID;
+                       g_free (fname);
+                       return NULL;
+               }
        }
        if (new_fname && new_fname != fname) {
                g_free (fname);
@@ -2596,10 +2604,12 @@ mono_assembly_load_with_partial_name (const char *name, MonoImageOpenStatus *sta
                MonoReflectionAssembly *refasm;
 
                refasm = mono_try_assembly_resolve (domain, mono_string_new (domain, name), NULL, FALSE, &error);
-               if (!mono_error_ok (&error)) {
+               if (!is_ok (&error)) {
                        g_free (fullname);
                        mono_assembly_name_free (aname);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_error_cleanup (&error);
+                       if (*status == MONO_IMAGE_OK)
+                               *status = MONO_IMAGE_IMAGE_INVALID;
                }
 
                if (refasm)
index 45c3da535940aa408e9d54d699273f3e94370fbf..5e1605fd972295a21362b31a4be27f3d4f7d61a7 100644 (file)
@@ -5,6 +5,7 @@
  *   Zoltan Varga (vargaz@gmail.com)
  *
  * Copyright 2007-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -301,18 +302,30 @@ mono_attach_load_agent (MonoDomain *domain, char *agent, char *args, MonoObject
                return 1;
        }
        
+       
+       main_args = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, (args == NULL) ? 0 : 1, &error);
+       if (main_args == NULL) {
+               g_print ("Could not allocate main method args due to %s\n", mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+               g_free (agent);
+               return 1;
+       }
+
        if (args) {
-               main_args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, 1);
                mono_array_set (main_args, MonoString*, 0, mono_string_new (domain, args));
-       } else {
-               main_args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, 0);
        }
 
-       g_free (agent);
 
        pa [0] = main_args;
        mono_runtime_try_invoke (method, NULL, pa, exc, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error)) {
+               g_print ("The entry point method of assembly '%s' could not be executed due to %s\n", agent, mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+               g_free (agent);
+               return 1;
+       }
+
+       g_free (agent);
 
        return 0;
 }
@@ -474,11 +487,14 @@ transport_start_receive (void)
 static guint32 WINAPI
 receiver_thread (void *arg)
 {
+       MonoError error;
        int res, content_len;
        guint8 buffer [256];
        guint8 *p, *p_end;
        MonoObject *exc;
 
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Attach receiver");
+
        printf ("attach: Listening on '%s'...\n", server_uri);
 
        while (TRUE) {
@@ -489,11 +505,13 @@ receiver_thread (void *arg)
 
                printf ("attach: Connected.\n");
 
-               mono_thread_attach (mono_get_root_domain ());
+               MonoThread *thread = mono_thread_attach (mono_get_root_domain ());
+               mono_thread_set_name_internal (thread->internal_thread, mono_string_new (mono_get_root_domain (), "Attach receiver"), TRUE, &error);
+               mono_error_assert_ok (&error);
                /* Ask the runtime to not abort this thread */
                //mono_thread_current ()->flags |= MONO_THREAD_FLAG_DONT_MANAGE;
                /* Ask the runtime to not wait for this thread */
-               mono_thread_internal_current ()->state |= ThreadState_Background;
+               thread->internal_thread->state |= ThreadState_Background;
 
                while (TRUE) {
                        char *cmd, *agent_name, *agent_args;
index 4834da608e17f422aecf9019bbda97c569fc1bcb..43844ad98304cfed42194dc622df44a161fe27ab 100644 (file)
@@ -4,6 +4,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011-2012 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index c8323fbe935a51f5649a502b17580f71472f8934..1e7404d4e0ca4f35fa84f5ce47c475a9b3694ef0 100644 (file)
@@ -1,5 +1,6 @@
 /* 
  * Copyright 2012 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_METADATA_CLASS_INTERNALS_H__
 #define __MONO_METADATA_CLASS_INTERNALS_H__
@@ -517,7 +518,6 @@ struct _MonoMethodInflated {
                MonoMethod method;
                MonoMethodPInvoke pinvoke;
        } method;
-       MonoMethodHeader *header;
        MonoMethod *declaring;          /* the generic method definition. */
        MonoGenericContext context;     /* The current instantiation */
        MonoImageSet *owner; /* The image set that the inflated method belongs to. */
@@ -721,16 +721,6 @@ typedef struct {
        gboolean no_raise;
 } MonoJitICallInfo;
 
-typedef struct {
-       guint8 exception_type;
-       char *class_name; /* If kind == TYPE */
-       char *assembly_name; /* If kind == TYPE or ASSEMBLY */
-       MonoClass *klass; /* If kind != TYPE */
-       const char *member_name; /* If kind != TYPE */
-       gboolean ref_only; /* If kind == ASSEMBLY */
-       char *msg; /* If kind == BAD_IMAGE */
-} MonoLoaderError;
-
 void
 mono_class_setup_supertypes (MonoClass *klass);
 
@@ -918,8 +908,6 @@ extern MonoStats mono_stats;
 typedef gpointer (*MonoRemotingTrampoline)       (MonoDomain *domain, MonoMethod *method, MonoRemotingTarget target);
 typedef gpointer (*MonoDelegateTrampoline)       (MonoDomain *domain, MonoClass *klass);
 
-typedef gpointer (*MonoLookupDynamicToken) (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context);
-
 typedef gboolean (*MonoGetCachedClassInfo) (MonoClass *klass, MonoCachedClassInfo *res);
 
 typedef gboolean (*MonoGetClassFromName) (MonoImage *image, const char *name_space, const char *name, MonoClass **res);
@@ -941,7 +929,7 @@ void
 mono_classes_cleanup (void);
 
 void
-mono_class_layout_fields   (MonoClass *klass);
+mono_class_layout_fields   (MonoClass *klass, int instance_size);
 
 void
 mono_class_setup_interface_offsets (MonoClass *klass);
@@ -1011,16 +999,13 @@ void
 mono_install_delegate_trampoline (MonoDelegateTrampoline func);
 
 gpointer
-mono_lookup_dynamic_token (MonoImage *image, guint32 token, MonoGenericContext *context);
+mono_lookup_dynamic_token (MonoImage *image, guint32 token, MonoGenericContext *context, MonoError *error);
 
 gpointer
-mono_lookup_dynamic_token_class (MonoImage *image, guint32 token, gboolean check_token, MonoClass **handle_class, MonoGenericContext *context);
-
-void
-mono_install_lookup_dynamic_token (MonoLookupDynamicToken func);
+mono_lookup_dynamic_token_class (MonoImage *image, guint32 token, gboolean check_token, MonoClass **handle_class, MonoGenericContext *context, MonoError *error);
 
 gpointer
-mono_runtime_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean add_sync_wrapper);
+mono_runtime_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean add_sync_wrapper, MonoError *error);
 
 gpointer
 mono_runtime_create_delegate_trampoline (MonoClass *klass);
@@ -1239,32 +1224,6 @@ mono_loader_lock_if_inited (void);
 void
 mono_loader_unlock_if_inited (void);
 
-void
-mono_loader_set_error_assembly_load (const char *assembly_name, gboolean ref_only);
-
-void
-mono_loader_set_error_type_load (const char *class_name, const char *assembly_name);
-
-void
-mono_loader_set_error_method_load (const char *class_name, const char *member_name);
-
-void
-mono_loader_set_error_field_load (MonoClass *klass, const char *member_name);
-void
-mono_loader_set_error_bad_image (char *msg);
-
-MonoException *
-mono_loader_error_prepare_exception (MonoLoaderError *error);
-
-MonoLoaderError *
-mono_loader_get_last_error (void);
-
-void
-mono_loader_clear_error    (void);
-
-void
-mono_loader_assert_no_error (void);
-
 void
 mono_reflection_init       (void);
 
index d264ea32ba65bb24b09f9e54628227e7023f5d0f..17da478b5e9c1f089d76de0bc275da6ab5e21077 100644 (file)
@@ -7,6 +7,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #ifdef HAVE_ALLOCA_H
@@ -285,15 +286,10 @@ mono_class_from_typeref_checked (MonoImage *image, guint32 type_token, MonoError
 done:
        /* Generic case, should be avoided for when a better error is possible. */
        if (!res && mono_error_ok (error)) {
-               if (mono_loader_get_last_error ()) { /*FIXME plug the above to not leak errors*/
-                       mono_error_set_from_loader_error (error);
-               } else {
-                       char *name = mono_class_name_from_token (image, type_token);
-                       char *assembly = mono_assembly_name_from_token (image, type_token);
-                       mono_error_set_type_load_name (error, name, assembly, "Could not resolve type with token %08x", type_token);
-               }
+               char *name = mono_class_name_from_token (image, type_token);
+               char *assembly = mono_assembly_name_from_token (image, type_token);
+               mono_error_set_type_load_name (error, name, assembly, "Could not resolve type with token %08x", type_token);
        }
-       mono_loader_assert_no_error ();
        return res;
 }
 
@@ -1134,11 +1130,11 @@ mono_class_inflate_generic_method_full_checked (MonoMethod *method, MonoClass *k
        result->sre_method = FALSE;
        result->signature = NULL;
 
-       if (!context->method_inst) {
+       if (iresult->context.method_inst) {
                /* Set the generic_container of the result to the generic_container of method */
                MonoGenericContainer *generic_container = mono_method_get_generic_container (method);
 
-               if (generic_container) {
+               if (generic_container && iresult->context.method_inst == generic_container->context.method_inst) {
                        result->is_generic = 1;
                        mono_method_set_generic_container (result, generic_container);
                }
@@ -1350,7 +1346,6 @@ mono_class_find_enum_basetype (MonoClass *klass, MonoError *error)
        mono_error_set_type_load_class (error, klass, "Could not find base type");
 
 fail:
-       mono_loader_assert_no_error ();
        return NULL;
 }
 
@@ -1480,6 +1475,7 @@ mono_class_setup_fields (MonoClass *klass)
        int i, blittable = TRUE;
        guint32 real_size = 0;
        guint32 packing_size = 0;
+       int instance_size;
        gboolean explicit_size;
        MonoClassField *field;
        MonoGenericContainer *container = NULL;
@@ -1555,7 +1551,7 @@ mono_class_setup_fields (MonoClass *klass)
                }
        }
 
-       klass->instance_size = 0;
+       instance_size = 0;
        if (!klass->rank)
                klass->sizes.class_size = 0;
 
@@ -1569,13 +1565,13 @@ mono_class_setup_fields (MonoClass *klass)
                                return;
                        }
                }
-               klass->instance_size += klass->parent->instance_size;
+               instance_size += klass->parent->instance_size;
                klass->min_align = klass->parent->min_align;
                /* we use |= since it may have been set already */
                klass->has_references |= klass->parent->has_references;
                blittable = klass->parent->blittable;
        } else {
-               klass->instance_size = sizeof (MonoObject);
+               instance_size = sizeof (MonoObject);
                klass->min_align = 1;
        }
 
@@ -1597,14 +1593,16 @@ mono_class_setup_fields (MonoClass *klass)
                        return;
                }
                klass->packing_size = packing_size;
-               real_size += klass->instance_size;
+               real_size += instance_size;
        }
 
        if (!top) {
                if (explicit_size && real_size) {
-                       klass->instance_size = MAX (real_size, klass->instance_size);
+                       instance_size = MAX (real_size, instance_size);
                }
                klass->blittable = blittable;
+               if (!klass->instance_size)
+                       klass->instance_size = instance_size;
                mono_memory_barrier ();
                klass->size_inited = 1;
                klass->fields_inited = 1;
@@ -1718,12 +1716,12 @@ mono_class_setup_fields (MonoClass *klass)
                return;
        }
        if (explicit_size && real_size) {
-               klass->instance_size = MAX (real_size, klass->instance_size);
+               instance_size = MAX (real_size, instance_size);
        }
 
        if (mono_class_has_failure (klass))
                return;
-       mono_class_layout_fields (klass);
+       mono_class_layout_fields (klass, instance_size);
 
        /*valuetypes can't be neither bigger than 1Mb or empty. */
        if (klass->valuetype && (klass->instance_size <= 0 || klass->instance_size > (0x100000 + sizeof (MonoObject))))
@@ -1804,6 +1802,7 @@ type_has_references (MonoClass *klass, MonoType *ftype)
 /*
  * mono_class_layout_fields:
  * @class: a class
+ * @instance_size: base instance size
  *
  * Compute the placement of fields inside an object or struct, according to
  * the layout rules and set the following fields in @class:
@@ -1816,7 +1815,7 @@ type_has_references (MonoClass *klass, MonoType *ftype)
  * LOCKING: this is supposed to be called with the loader lock held.
  */
 void
-mono_class_layout_fields (MonoClass *klass)
+mono_class_layout_fields (MonoClass *klass, int instance_size)
 {
        int i;
        const int top = klass->field.count;
@@ -1897,7 +1896,6 @@ mono_class_layout_fields (MonoClass *klass)
        /*
         * Compute field layout and total size (not considering static fields)
         */
-
        switch (layout) {
        case TYPE_ATTRIBUTE_AUTO_LAYOUT:
        case TYPE_ATTRIBUTE_SEQUENTIAL_LAYOUT:
@@ -1973,11 +1971,11 @@ mono_class_layout_fields (MonoClass *klass)
                                real_size = field->offset + size;
                        }
 
-                       klass->instance_size = MAX (real_size, klass->instance_size);
+                       instance_size = MAX (real_size, instance_size);
        
-                       if (klass->instance_size & (klass->min_align - 1)) {
-                               klass->instance_size += klass->min_align - 1;
-                               klass->instance_size &= ~(klass->min_align - 1);
+                       if (instance_size & (klass->min_align - 1)) {
+                               instance_size += klass->min_align - 1;
+                               instance_size &= ~(klass->min_align - 1);
                        }
                }
                break;
@@ -2062,10 +2060,10 @@ mono_class_layout_fields (MonoClass *klass)
                        g_free (ref_bitmap);
                }
 
-               klass->instance_size = MAX (real_size, klass->instance_size);
-               if (klass->instance_size & (klass->min_align - 1)) {
-                       klass->instance_size += klass->min_align - 1;
-                       klass->instance_size &= ~(klass->min_align - 1);
+               instance_size = MAX (real_size, instance_size);
+               if (instance_size & (klass->min_align - 1)) {
+                       instance_size += klass->min_align - 1;
+                       instance_size &= ~(klass->min_align - 1);
                }
                break;
        }
@@ -2081,11 +2079,17 @@ mono_class_layout_fields (MonoClass *klass)
                 * unaligned accesses otherwise. See #78990 for a testcase.
                 */
                if (mono_align_small_structs) {
-                       if (klass->instance_size <= sizeof (MonoObject) + sizeof (gpointer))
-                               klass->min_align = MAX (klass->min_align, klass->instance_size - sizeof (MonoObject));
+                       if (instance_size <= sizeof (MonoObject) + sizeof (gpointer))
+                               klass->min_align = MAX (klass->min_align, instance_size - sizeof (MonoObject));
                }
        }
 
+       if (klass->instance_size && !klass->image->dynamic) {
+               /* Might be already set using cached info */
+               g_assert (klass->instance_size == instance_size);
+       } else {
+               klass->instance_size = instance_size;
+       }
        mono_memory_barrier ();
        klass->size_inited = 1;
 
@@ -3792,6 +3796,7 @@ mono_class_setup_vtable (MonoClass *klass)
 static void
 mono_class_setup_vtable_full (MonoClass *klass, GList *in_setup)
 {
+       MonoError error;
        MonoMethod **overrides;
        MonoGenericContext *context;
        guint32 type_token;
@@ -3842,7 +3847,14 @@ mono_class_setup_vtable_full (MonoClass *klass, GList *in_setup)
                 * This is true since we don't do layout all over again for them, we simply inflate
                 * the layout of the parent.
                 */
-               mono_reflection_get_dynamic_overrides (klass, &overrides, &onum);
+               mono_reflection_get_dynamic_overrides (klass, &overrides, &onum, &error);
+               if (!is_ok (&error)) {
+                       mono_loader_unlock ();
+                       g_list_remove (in_setup, klass);
+                       mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, g_strdup_printf("Could not load list of method overrides due to %s", mono_error_get_message (&error)));
+                       mono_error_cleanup (&error);
+                       return;
+               }
        } else {
                /* The following call fails if there are missing methods in the type */
                /* FIXME it's probably a good idea to avoid this for generic instances. */
@@ -5017,59 +5029,6 @@ concat_two_strings_with_zero (MonoImage *image, const char *s1, const char *s2)
        return s;
 }
 
-static void
-set_failure_from_loader_error (MonoClass *klass, MonoLoaderError *error)
-{
-       gpointer exception_data = NULL;
-
-       switch (error->exception_type) {
-       case MONO_EXCEPTION_TYPE_LOAD:
-               exception_data = concat_two_strings_with_zero (klass->image, error->class_name, error->assembly_name);
-               break;
-
-       case MONO_EXCEPTION_MISSING_METHOD:
-               exception_data = concat_two_strings_with_zero (klass->image, error->class_name, error->member_name);
-               break;
-
-       case MONO_EXCEPTION_MISSING_FIELD: {
-               const char *name_space = error->klass->name_space ? error->klass->name_space : NULL;
-               const char *class_name;
-
-               if (name_space)
-                       class_name = g_strdup_printf ("%s.%s", name_space, error->klass->name);
-               else
-                       class_name = error->klass->name;
-
-               exception_data = concat_two_strings_with_zero (klass->image, class_name, error->member_name);
-               
-               if (name_space)
-                       g_free ((void*)class_name);
-               break;
-       }
-
-       case MONO_EXCEPTION_FILE_NOT_FOUND: {
-               const char *msg;
-
-               if (error->ref_only)
-                       msg = "Cannot resolve dependency to assembly '%s' because it has not been preloaded. When using the ReflectionOnly APIs, dependent assemblies must be pre-loaded or loaded on demand through the ReflectionOnlyAssemblyResolve event.";
-               else
-                       msg = "Could not load file or assembly '%s' or one of its dependencies.";
-
-               exception_data = concat_two_strings_with_zero (klass->image, msg, error->assembly_name);
-               break;
-       }
-
-       case MONO_EXCEPTION_BAD_IMAGE:
-               exception_data = error->msg;
-               break;
-
-       default :
-               g_assert_not_reached ();
-       }
-
-       mono_class_set_failure (klass, error->exception_type, exception_data);
-}
-
 /**
  * mono_class_init:
  * @class: the class to initialize
@@ -5175,7 +5134,7 @@ mono_class_init (MonoClass *klass)
        else
                if (!klass->size_inited){
                        mono_class_setup_fields (klass);
-                       if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+                       if (mono_class_has_failure (klass))
                                goto leave;
                }
                                
@@ -5284,8 +5243,6 @@ mono_class_init (MonoClass *klass)
                        mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
                        goto leave;
                }
-               if (mono_loader_get_last_error ())
-                       goto leave;
                if (!klass->parent->vtable_size) {
                        /* FIXME: Get rid of this somehow */
                        mono_class_setup_vtable (klass->parent);
@@ -5293,8 +5250,6 @@ mono_class_init (MonoClass *klass)
                                mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
                                goto leave;
                        }
-                       if (mono_loader_get_last_error ())
-                               goto leave;
                }
                first_iface_slot = klass->parent->vtable_size;
                if (mono_class_need_stelemref_method (klass))
@@ -5307,13 +5262,6 @@ mono_class_init (MonoClass *klass)
        if (mono_security_core_clr_enabled ())
                mono_security_core_clr_check_inheritance (klass);
 
-       if (mono_loader_get_last_error ()) {
-               if (!mono_class_has_failure (klass)) {
-                       set_failure_from_loader_error (klass, mono_loader_get_last_error ());
-               }
-               mono_loader_clear_error ();
-       }
-
        if (klass->generic_class && !mono_verifier_class_is_valid_generic_instantiation (klass))
                mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, g_strdup ("Invalid generic instantiation"));
 
@@ -5362,7 +5310,7 @@ mono_class_has_finalizer (MonoClass *klass)
                                 * ignores overrides.
                                 */
                                mono_class_setup_vtable (klass);
-                               if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+                               if (mono_class_has_failure (klass))
                                        cmethod = NULL;
                                else
                                        cmethod = klass->vtable [finalize_slot];
@@ -5747,7 +5695,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
 
        if (mono_metadata_token_table (type_token) != MONO_TABLE_TYPEDEF || tidx > tt->rows) {
                mono_error_set_bad_image (error, image, "Invalid typedef token %x", type_token);
-               mono_loader_assert_no_error ();
                return NULL;
        }
 
@@ -5755,7 +5702,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
 
        if ((klass = (MonoClass *)mono_internal_hash_table_lookup (&image->class_cache, GUINT_TO_POINTER (type_token)))) {
                mono_loader_unlock ();
-               mono_loader_assert_no_error ();
                return klass;
        }
 
@@ -5845,7 +5791,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
                        mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, g_strdup (mono_error_get_message (error)));
                        mono_loader_unlock ();
                        mono_profiler_class_loaded (klass, MONO_PROFILE_FAILED);
-                       mono_loader_assert_no_error ();
                        return NULL;
                }
        }
@@ -5917,7 +5862,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
                        mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, g_strdup (mono_error_get_message (error)));
                        mono_loader_unlock ();
                        mono_profiler_class_loaded (klass, MONO_PROFILE_FAILED);
-                       mono_loader_assert_no_error ();
                        return NULL;
                }
                klass->cast_class = klass->element_class = mono_class_from_mono_type (enum_basetype);
@@ -5932,7 +5876,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
                mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, g_strdup_printf ("Could not load generic parameter constrains due to %s", mono_error_get_message (error)));
                mono_loader_unlock ();
                mono_profiler_class_loaded (klass, MONO_PROFILE_FAILED);
-               mono_loader_assert_no_error ();
                return NULL;
        }
 
@@ -5944,7 +5887,6 @@ mono_class_create_from_typedef (MonoImage *image, guint32 type_token, MonoError
        mono_loader_unlock ();
 
        mono_profiler_class_loaded (klass, MONO_PROFILE_OK);
-       mono_loader_assert_no_error ();
 
        return klass;
 
@@ -5952,7 +5894,6 @@ parent_failure:
        mono_class_setup_mono_type (klass);
        mono_loader_unlock ();
        mono_profiler_class_loaded (klass, MONO_PROFILE_FAILED);
-       mono_loader_assert_no_error ();
        return NULL;
 }
 
@@ -6617,7 +6558,6 @@ mono_type_retrieve_from_typespec (MonoImage *image, guint32 type_spec, MonoGener
                MonoType *inflated = inflate_generic_type (NULL, t, context, error);
 
                if (!mono_error_ok (error)) {
-                       mono_loader_assert_no_error ();
                        return NULL;
                }
 
@@ -7440,7 +7380,7 @@ mono_class_get_checked (MonoImage *image, guint32 type_token, MonoError *error)
                        mono_error_set_bad_image (error, image,"Bad token table for dynamic image: %x", table);
                        return NULL;
                }
-               klass = (MonoClass *)mono_lookup_dynamic_token (image, type_token, NULL); /*FIXME proper error handling*/
+               klass = (MonoClass *)mono_lookup_dynamic_token (image, type_token, NULL, error);
                goto done;
        }
 
@@ -7490,14 +7430,16 @@ mono_type_get_checked (MonoImage *image, guint32 type_token, MonoGenericContext
        mono_error_init (error);
 
        //FIXME: this will not fix the very issue for which mono_type_get_full exists -but how to do it then?
-       if (image_is_dynamic (image))
-               return mono_class_get_type ((MonoClass *)mono_lookup_dynamic_token (image, type_token, context));
+       if (image_is_dynamic (image)) {
+               MonoClass *klass = (MonoClass *)mono_lookup_dynamic_token (image, type_token, context, error);
+               return_val_if_nok (error, NULL);
+               return mono_class_get_type (klass);
+       }
 
        if ((type_token & 0xff000000) != MONO_TOKEN_TYPE_SPEC) {
                MonoClass *klass = mono_class_get_checked (image, type_token, error);
 
                if (!klass) {
-                       mono_loader_assert_no_error ();
                        return NULL;
                }
 
@@ -7508,7 +7450,6 @@ mono_type_get_checked (MonoImage *image, guint32 type_token, MonoGenericContext
        type = mono_type_retrieve_from_typespec (image, type_token, context, &inflated, error);
 
        if (!type) {
-               mono_loader_assert_no_error ();
                return NULL;
        }
 
@@ -8317,6 +8258,7 @@ mono_gparam_is_assignable_from (MonoClass *target, MonoClass *candidate)
 gboolean
 mono_class_is_assignable_from (MonoClass *klass, MonoClass *oklass)
 {
+       MonoError error;
        /*FIXME this will cause a lot of irrelevant stuff to be loaded.*/
        if (!klass->inited)
                mono_class_init (klass);
@@ -8350,12 +8292,18 @@ mono_class_is_assignable_from (MonoClass *klass, MonoClass *oklass)
                }
 
                /* interface_offsets might not be set for dynamic classes */
-               if (oklass->ref_info_handle && !oklass->interface_bitmap)
+               if (oklass->ref_info_handle && !oklass->interface_bitmap) {
                        /* 
                         * oklass might be a generic type parameter but they have 
                         * interface_offsets set.
                         */
-                       return mono_reflection_call_is_assignable_to (oklass, klass);
+                       gboolean result = mono_reflection_call_is_assignable_to (oklass, klass, &error);
+                       if (!is_ok (&error)) {
+                               mono_error_cleanup (&error);
+                               return FALSE;
+                       }
+                       return result;
+               }
                if (!oklass->interface_bitmap)
                        /* Happens with generic instances of not-yet created dynamic types */
                        return FALSE;
@@ -8363,7 +8311,6 @@ mono_class_is_assignable_from (MonoClass *klass, MonoClass *oklass)
                        return TRUE;
 
                if (mono_class_has_variant_generic_params (klass)) {
-                       MonoError error;
                        int i;
                        mono_class_setup_interfaces (oklass, &error);
                        if (!mono_error_ok (&error)) {
@@ -8760,8 +8707,9 @@ mono_ldtoken_checked (MonoImage *image, guint32 token, MonoClass **handle_class,
 
        if (image_is_dynamic (image)) {
                MonoClass *tmp_handle_class;
-               gpointer obj = mono_lookup_dynamic_token_class (image, token, TRUE, &tmp_handle_class, context);
+               gpointer obj = mono_lookup_dynamic_token_class (image, token, TRUE, &tmp_handle_class, context, error);
 
+               mono_error_assert_ok (error);
                g_assert (tmp_handle_class);
                if (handle_class)
                        *handle_class = tmp_handle_class;
@@ -8841,30 +8789,18 @@ mono_ldtoken_checked (MonoImage *image, guint32 token, MonoClass **handle_class,
        return NULL;
 }
 
-/**
- * This function might need to call runtime functions so it can't be part
- * of the metadata library.
- */
-static MonoLookupDynamicToken lookup_dynamic = NULL;
-
-void
-mono_install_lookup_dynamic_token (MonoLookupDynamicToken func)
-{
-       lookup_dynamic = func;
-}
-
 gpointer
-mono_lookup_dynamic_token (MonoImage *image, guint32 token, MonoGenericContext *context)
+mono_lookup_dynamic_token (MonoImage *image, guint32 token, MonoGenericContext *context, MonoError *error)
 {
        MonoClass *handle_class;
-
-       return lookup_dynamic (image, token, TRUE, &handle_class, context);
+       mono_error_init (error);
+       return mono_reflection_lookup_dynamic_token (image, token, TRUE, &handle_class, context, error);
 }
 
 gpointer
-mono_lookup_dynamic_token_class (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context)
+mono_lookup_dynamic_token_class (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context, MonoError *error)
 {
-       return lookup_dynamic (image, token, valid_token, handle_class, context);
+       return mono_reflection_lookup_dynamic_token (image, token, valid_token, handle_class, context, error);
 }
 
 static MonoGetCachedClassInfo get_cached_class_info = NULL;
@@ -10062,17 +9998,8 @@ mono_class_get_exception_for_failure (MonoClass *klass)
                return mono_exception_from_name_msg (mono_defaults.corlib, "System", "InvalidProgramException", "");
        }
        default: {
-               MonoLoaderError *error;
-               MonoException *ex;
-               
-               error = mono_loader_get_last_error ();
-               if (error != NULL){
-                       ex = mono_loader_error_prepare_exception (error);
-                       return ex;
-               }
-               
                /* TODO - handle other class related failures */
-               return NULL;
+               return mono_get_exception_execution_engine ("Unknown class failure");
        }
        }
 }
index 2adee418f37749a9f80db8f8f49a95e75d0b8640..3ebe507d0d185472c7aada8bed2713c8b11847df 100644 (file)
@@ -97,7 +97,6 @@ GENERATE_GET_CLASS_WITH_CACHE (variant,    System, Variant)
 
 static GENERATE_GET_CLASS_WITH_CACHE (interface_type_attribute, System.Runtime.InteropServices, InterfaceTypeAttribute)
 static GENERATE_GET_CLASS_WITH_CACHE (guid_attribute, System.Runtime.InteropServices, GuidAttribute)
-static GENERATE_GET_CLASS_WITH_CACHE (com_visible_attribute, System.Runtime.InteropServices, ComVisibleAttribute)
 
 /* Upon creation of a CCW, only allocate a weak handle and set the
  * reference count to 0. If the unmanaged client code decides to addref and
@@ -149,6 +148,10 @@ cominterop_get_managed_wrapper_adjusted (MonoMethod *method);
 static gpointer
 cominterop_get_ccw (MonoObject* object, MonoClass* itf);
 
+static gpointer
+cominterop_get_ccw_checked (MonoObject *object, MonoClass *itf, MonoError *error);
+
+
 static MonoObject*
 cominterop_get_ccw_object (MonoCCWInterface* ccw_entry, gboolean verify);
 
@@ -465,7 +468,7 @@ cominterop_com_visible (MonoClass* klass)
 
 }
 
-static void cominterop_raise_hr_exception (int hr)
+static void cominterop_set_hr_error (MonoError *oerror, int hr)
 {
        static MonoMethod* throw_exception_for_hr = NULL;
        MonoError error;
@@ -476,26 +479,29 @@ static void cominterop_raise_hr_exception (int hr)
                throw_exception_for_hr = mono_class_get_method_from_name (mono_defaults.marshal_class, "GetExceptionForHR", 1);
 
        ex = (MonoException*)mono_runtime_invoke_checked (throw_exception_for_hr, NULL, params, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_assert_ok (&error);
 
-       mono_raise_exception (ex);
+       mono_error_set_exception_instance (oerror, ex);
 }
 
 /**
- * cominterop_get_interface:
+ * cominterop_get_interface_checked:
  * @obj: managed wrapper object containing COM object
  * @ic: interface type to retrieve for COM object
+ * @error: set on error
  *
- * Returns: the COM interface requested
+ * Returns: the COM interface requested. On failure returns NULL and sets @error
  */
 static gpointer
-cominterop_get_interface (MonoComObject* obj, MonoClass* ic, gboolean throw_exception)
+cominterop_get_interface_checked (MonoComObject* obj, MonoClass* ic, MonoError *error)
 {
        gpointer itf = NULL;
 
        g_assert (ic);
        g_assert (MONO_CLASS_IS_INTERFACE (ic));
 
+       mono_error_init (error);
+
        mono_cominterop_lock ();
        if (obj->itf_hash)
                itf = g_hash_table_lookup (obj->itf_hash, GUINT_TO_POINTER ((guint)ic->interface_id));
@@ -507,8 +513,8 @@ cominterop_get_interface (MonoComObject* obj, MonoClass* ic, gboolean throw_exce
                int hr;
                g_assert(found);
                hr = ves_icall_System_Runtime_InteropServices_Marshal_QueryInterfaceInternal (obj->iunknown, iid, &itf);
-               if (hr < 0 && throw_exception) {
-                       cominterop_raise_hr_exception (hr);     
+               if (hr < 0) {
+                       cominterop_set_hr_error (error, hr);
                }
 
                if (hr >= 0 && itf) {
@@ -520,6 +526,30 @@ cominterop_get_interface (MonoComObject* obj, MonoClass* ic, gboolean throw_exce
                }
 
        }
+       return itf;
+}
+
+/**
+ * cominterop_get_interface:
+ * @obj: managed wrapper object containing COM object
+ * @ic: interface type to retrieve for COM object
+ *
+ * Returns: the COM interface requested
+ */
+static gpointer
+cominterop_get_interface (MonoComObject *obj, MonoClass *ic, gboolean throw_exception)
+{
+       MonoError error;
+       gpointer itf = cominterop_get_interface_checked (obj, ic, &error);
+       if (!is_ok (&error)) {
+               if (throw_exception) {
+                       mono_error_set_pending_exception (&error);
+                       return NULL;
+               } else {
+                       mono_error_cleanup (&error);
+               }
+       }
+
        if (throw_exception)
                g_assert (itf);
 
@@ -544,7 +574,7 @@ cominterop_type_from_handle (MonoType *handle)
        mono_class_init (klass);
 
        ret = mono_type_get_object_checked (domain, handle, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -592,6 +622,7 @@ mono_cominterop_cleanup (void)
 void
 mono_mb_emit_cominterop_call (MonoMethodBuilder *mb, MonoMethodSignature *sig, MonoMethod* method)
 {
+#ifndef DISABLE_JIT
        // get function pointer from 1st arg, the COM interface pointer
        mono_mb_emit_ldarg (mb, 0);
        mono_mb_emit_icon (mb, cominterop_get_com_slot_for_method (method));
@@ -602,11 +633,13 @@ mono_mb_emit_cominterop_call (MonoMethodBuilder *mb, MonoMethodSignature *sig, M
        mono_mb_emit_calli (mb, sig);
        mono_mb_emit_byte (mb, MONO_CUSTOM_PREFIX);
        mono_mb_emit_byte (mb, CEE_MONO_RESTORE_LMF);
+#endif /* DISABLE_JIT */
 }
 
 void
 mono_cominterop_emit_ptr_to_object_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv conv, MonoMarshalSpec *mspec)
 {
+#ifndef DISABLE_JIT
        switch (conv) {
        case MONO_MARSHAL_CONV_OBJECT_INTERFACE:
        case MONO_MARSHAL_CONV_OBJECT_IUNKNOWN:
@@ -678,11 +711,13 @@ mono_cominterop_emit_ptr_to_object_conv (MonoMethodBuilder *mb, MonoType *type,
        default:
                g_assert_not_reached ();
        }
+#endif /* DISABLE_JIT */
 }
 
 void
 mono_cominterop_emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv conv, MonoMarshalSpec *mspec)
 {
+#ifndef DISABLE_JIT
        switch (conv) {
        case MONO_MARSHAL_CONV_OBJECT_INTERFACE:
        case MONO_MARSHAL_CONV_OBJECT_IDISPATCH:
@@ -770,6 +805,7 @@ mono_cominterop_emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type,
        default:
                g_assert_not_reached ();
        }
+#endif /* DISABLE_JIT */
 }
 
 /**
@@ -906,6 +942,7 @@ mono_cominterop_get_native_wrapper (MonoMethod *method)
        sig = mono_method_signature (method);
        mb = mono_mb_new (method->klass, method->name, MONO_WRAPPER_COMINTEROP);
 
+#ifndef DISABLE_JIT
        /* if method klass is import, that means method
         * is really a com call. let interop system emit it.
        */
@@ -979,6 +1016,8 @@ mono_cominterop_get_native_wrapper (MonoMethod *method)
                        imported classes is not yet implemented.");
                mono_mb_emit_exception (mb, "NotSupportedException", msg);
        }
+#endif /* DISABLE_JIT */
+
        csig = mono_metadata_signature_dup_full (method->klass->image, sig);
        csig->pinvoke = 0;
        res = mono_mb_create_and_cache (cache, method,
@@ -1018,6 +1057,7 @@ mono_cominterop_get_invoke (MonoMethod *method)
 
        mb = mono_mb_new (method->klass, method->name, MONO_WRAPPER_COMINTEROP_INVOKE);
 
+#ifndef DISABLE_JIT
        /* get real proxy object, which is a ComInteropProxy in this case*/
        mono_mb_add_local (mb, &mono_defaults.object_class->byval_arg);
        mono_mb_emit_ldarg (mb, 0);
@@ -1058,6 +1098,7 @@ mono_cominterop_get_invoke (MonoMethod *method)
        mono_marshal_emit_thread_interrupt_checkpoint (mb);
 
        mono_mb_emit_byte (mb, CEE_RET);
+#endif /* DISABLE_JIT */
 
        res = mono_mb_create_and_cache (cache, method, mb, sig, sig->param_count + 16);
        mono_mb_free (mb);
@@ -1112,6 +1153,18 @@ mono_cominterop_emit_marshal_com_interface (EmitMarshalContext *m, int argnum,
        if (!marshal_release)
                marshal_release = mono_class_get_method_from_name (mono_defaults.marshal_class, "Release", 1);
 
+#ifdef DISABLE_JIT
+       switch (action) {
+       case MARSHAL_ACTION_CONV_IN:
+               *conv_arg_type = &mono_defaults.int_class->byval_arg;
+               break;
+       case MARSHAL_ACTION_MANAGED_CONV_IN:
+               *conv_arg_type = &mono_defaults.int_class->byval_arg;
+               break;
+       default:
+               break;
+       }
+#else
        switch (action) {
        case MARSHAL_ACTION_CONV_IN: {
                guint32 pos_null = 0;
@@ -1398,6 +1451,7 @@ mono_cominterop_emit_marshal_com_interface (EmitMarshalContext *m, int argnum,
        default:
                g_assert_not_reached ();
        }
+#endif /* DISABLE_JIT */
 
        return conv_arg;
 }
@@ -1449,20 +1503,23 @@ static gboolean cominterop_can_support_dispatch (MonoClass* klass)
 }
 
 static void*
-cominterop_get_idispatch_for_object (MonoObject* object)
+cominterop_get_idispatch_for_object (MonoObject* object, MonoError *error)
 {
+       mono_error_init (error);
        if (!object)
                return NULL;
 
        if (cominterop_object_is_rcw (object)) {
-               return cominterop_get_interface (((MonoComInteropProxy*)((MonoTransparentProxy*)object)->rp)->com_object, 
-                       mono_class_get_idispatch_class (), TRUE);
+               return cominterop_get_interface_checked (((MonoComInteropProxy*)((MonoTransparentProxy*)object)->rp)->com_object,
+                                                        mono_class_get_idispatch_class (), error);
        }
        else {
                MonoClass* klass = mono_object_class (object);
-               if (!cominterop_can_support_dispatch (klass) )
-                       cominterop_raise_hr_exception (MONO_E_NOINTERFACE);
-               return cominterop_get_ccw (object, mono_class_get_idispatch_class ());
+               if (!cominterop_can_support_dispatch (klass) ) {
+                       cominterop_set_hr_error (error, MONO_E_NOINTERFACE);
+                       return NULL;
+               }
+               return cominterop_get_ccw_checked (object, mono_class_get_idispatch_class (), error);
        }
 }
 
@@ -1470,6 +1527,8 @@ void*
 ves_icall_System_Runtime_InteropServices_Marshal_GetIUnknownForObjectInternal (MonoObject* object)
 {
 #ifndef DISABLE_COM
+       MonoError error;
+
        if (!object)
                return NULL;
 
@@ -1504,7 +1563,9 @@ ves_icall_System_Runtime_InteropServices_Marshal_GetIUnknownForObjectInternal (M
                return ((MonoComInteropProxy*)real_proxy)->com_object->iunknown;
        }
        else {
-               return cominterop_get_ccw (object, mono_class_get_iunknown_class ());
+               void* ccw_entry = cominterop_get_ccw_checked (object, mono_class_get_iunknown_class (), &error);
+               mono_error_set_pending_exception (&error);
+               return ccw_entry;
        }
 #else
        g_assert_not_reached ();
@@ -1533,7 +1594,10 @@ void*
 ves_icall_System_Runtime_InteropServices_Marshal_GetIDispatchForObjectInternal (MonoObject* object)
 {
 #ifndef DISABLE_COM
-       return cominterop_get_idispatch_for_object (object);
+       MonoError error;
+       void* idisp = cominterop_get_idispatch_for_object (object, &error);
+       mono_error_set_pending_exception (&error);
+       return idisp;
 #else
        g_assert_not_reached ();
 #endif
@@ -1543,6 +1607,7 @@ void*
 ves_icall_System_Runtime_InteropServices_Marshal_GetCCW (MonoObject* object, MonoReflectionType* type)
 {
 #ifndef DISABLE_COM
+       MonoError error;
        MonoClass* klass = NULL;
        void* itf = NULL;
        g_assert (type);
@@ -1554,8 +1619,8 @@ ves_icall_System_Runtime_InteropServices_Marshal_GetCCW (MonoObject* object, Mon
                return NULL;
        }
 
-       itf = cominterop_get_ccw (object, klass);
-       g_assert (itf);
+       itf = cominterop_get_ccw_checked (object, klass, &error);
+       mono_error_set_pending_exception (&error);
        return itf;
 #else
        g_assert_not_reached ();
@@ -1712,13 +1777,19 @@ gpointer
 ves_icall_System_ComObject_GetInterfaceInternal (MonoComObject* obj, MonoReflectionType* type, MonoBoolean throw_exception)
 {
 #ifndef DISABLE_COM
+       MonoError error;
        MonoClass *klass = mono_type_get_class (type->type);
        if (!mono_class_init (klass)) {
                mono_set_pending_exception (mono_class_get_exception_for_failure (klass));
                return NULL;
        }
 
-       return cominterop_get_interface (obj, klass, (gboolean)throw_exception);
+       gpointer itf = cominterop_get_interface_checked (obj, klass, &error);
+       if (throw_exception)
+               mono_error_set_pending_exception (&error);
+       else
+               mono_error_cleanup (&error);
+       return itf;
 #else
        g_assert_not_reached ();
 #endif
@@ -1826,17 +1897,18 @@ cominterop_setup_marshal_context (EmitMarshalContext *m, MonoMethod *method)
 }
 
 /**
- * cominterop_get_ccw:
+ * cominterop_get_ccw_checked:
  * @object: a pointer to the object
  * @itf: interface type needed
+ * @error: set on error
  *
  * Returns: a value indicating if the object is a
- * Runtime Callable Wrapper (RCW) for a COM object
+ * Runtime Callable Wrapper (RCW) for a COM object.
+ * On failure returns NULL and sets @error.
  */
 static gpointer
-cominterop_get_ccw (MonoObject* object, MonoClass* itf)
+cominterop_get_ccw_checked (MonoObject* object, MonoClass* itf, MonoError *error)
 {
-       MonoError error;
        int i;
        MonoCCW *ccw = NULL;
        MonoCCWInterface* ccw_entry = NULL;
@@ -1851,6 +1923,8 @@ cominterop_get_ccw (MonoObject* object, MonoClass* itf)
        GList *ccw_list, *ccw_list_item;
        MonoCustomAttrInfo *cinfo = NULL;
 
+       mono_error_init (error);
+       
        if (!object)
                return NULL;
 
@@ -1908,12 +1982,12 @@ cominterop_get_ccw (MonoObject* object, MonoClass* itf)
                g_hash_table_insert (ccw_hash, GINT_TO_POINTER (mono_object_hash (object)), ccw_list);
                mono_cominterop_unlock ();
                /* register for finalization to clean up ccw */
-               mono_object_register_finalizer (object, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_object_register_finalizer (object, error);
+               return_val_if_nok (error, NULL);
        }
 
-       cinfo = mono_custom_attrs_from_class_checked (itf, &error);
-       mono_error_assert_ok (&error);
+       cinfo = mono_custom_attrs_from_class_checked (itf, error);
+       mono_error_assert_ok (error);
        if (cinfo) {
                static MonoClass* coclass_attribute = NULL;
                if (!coclass_attribute)
@@ -2027,8 +2101,10 @@ cominterop_get_ccw (MonoObject* object, MonoClass* itf)
                                mspecs [0] = NULL;
                        }
 
+#ifndef DISABLE_JIT
                        /* skip visiblity since we call internal methods */
                        mb->skip_visibility = TRUE;
+#endif
 
                        cominterop_setup_marshal_context (&m, adjust_method);
                        m.mb = mb;
@@ -2039,7 +2115,6 @@ cominterop_get_ccw (MonoObject* object, MonoClass* itf)
 
                        vtable [vtable_index--] = mono_compile_method (wrapper_method);
 
-                       
                        for (param_index = sig_adjusted->param_count; param_index >= 0; param_index--)
                                if (mspecs [param_index])
                                        mono_metadata_free_marshal_spec (mspecs [param_index]);
@@ -2056,6 +2131,23 @@ cominterop_get_ccw (MonoObject* object, MonoClass* itf)
        return ccw_entry;
 }
 
+/**
+ * cominterop_get_ccw:
+ * @object: a pointer to the object
+ * @itf: interface type needed
+ *
+ * Returns: a value indicating if the object is a
+ * Runtime Callable Wrapper (RCW) for a COM object
+ */
+static gpointer
+cominterop_get_ccw (MonoObject* object, MonoClass* itf)
+{
+       MonoError error;
+       gpointer ccw_entry = cominterop_get_ccw_checked (object, itf, &error);
+       mono_error_set_pending_exception (&error);
+       return ccw_entry;
+}
+
 static gboolean
 mono_marshal_free_ccw_entry (gpointer key, gpointer value, gpointer user_data)
 {
@@ -2182,9 +2274,9 @@ cominterop_get_managed_wrapper_adjusted (MonoMethod *method)
 
        mspecs [0] = NULL;
 
-       if (!preserve_sig) {
+#ifndef DISABLE_JIT
+       if (!preserve_sig)
                hr = mono_mb_add_local (mb, &mono_defaults.int32_class->byval_arg);
-       }
        else if (!MONO_TYPE_IS_VOID (sig->ret))
                hr = mono_mb_add_local (mb, sig->ret);
 
@@ -2248,6 +2340,7 @@ cominterop_get_managed_wrapper_adjusted (MonoMethod *method)
                mono_mb_emit_ldloc (mb, hr);
 
        mono_mb_emit_byte (mb, CEE_RET);
+#endif /* DISABLE_JIT */
 
        mono_cominterop_lock ();
        res = mono_mb_create_method (mb, sig_native, sig_native->param_count + 16);     
@@ -2334,10 +2427,12 @@ static int
 cominterop_ccw_getfreethreadedmarshaler (MonoCCW* ccw, MonoObject* object, gpointer* ppv)
 {
 #ifdef HOST_WIN32
+       MonoError error;
        if (!ccw->free_marshaler) {
                int ret = 0;
                gpointer tunk;
-               tunk = cominterop_get_ccw (object, mono_class_get_iunknown_class ());
+               tunk = cominterop_get_ccw_checked (object, mono_class_get_iunknown_class (), &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
                ret = CoCreateFreeThreadedMarshaler (tunk, (LPUNKNOWN*)&ccw->free_marshaler);
        }
                
@@ -2374,7 +2469,8 @@ cominterop_ccw_queryinterface (MonoCCWInterface* ccwe, guint8* riid, gpointer* p
 
        /* handle IUnknown special */
        if (cominterop_class_guid_equal (riid, mono_class_get_iunknown_class ())) {
-               *ppv = cominterop_get_ccw (object, mono_class_get_iunknown_class ());
+               *ppv = cominterop_get_ccw_checked (object, mono_class_get_iunknown_class (), &error);
+               mono_error_assert_ok (&error);
                /* remember to addref on QI */
                cominterop_ccw_addref ((MonoCCWInterface *)*ppv);
                return MONO_S_OK;
@@ -2385,7 +2481,8 @@ cominterop_ccw_queryinterface (MonoCCWInterface* ccwe, guint8* riid, gpointer* p
                if (!cominterop_can_support_dispatch (klass))
                        return MONO_E_NOINTERFACE;
                
-               *ppv = cominterop_get_ccw (object, mono_class_get_idispatch_class ());
+               *ppv = cominterop_get_ccw_checked (object, mono_class_get_idispatch_class (), &error);
+               mono_error_assert_ok (&error);
                /* remember to addref on QI */
                cominterop_ccw_addref ((MonoCCWInterface *)*ppv);
                return MONO_S_OK;
@@ -2419,7 +2516,11 @@ cominterop_ccw_queryinterface (MonoCCWInterface* ccwe, guint8* riid, gpointer* p
                klass_iter = klass_iter->parent;
        }
        if (itf) {
-               *ppv = cominterop_get_ccw (object, itf);
+               *ppv = cominterop_get_ccw_checked (object, itf, &error);
+               if (!is_ok (&error)) {
+                       mono_error_cleanup (&error); /* FIXME don't swallow the error */
+                       return MONO_E_NOINTERFACE;
+               }
                /* remember to addref on QI */
                cominterop_ccw_addref ((MonoCCWInterface *)*ppv);
                return MONO_S_OK;
@@ -2731,10 +2832,9 @@ mono_cominterop_emit_marshal_safearray (EmitMarshalContext *m, int argnum, MonoT
 {
        MonoMethodBuilder *mb = m->mb;
 
+#ifndef DISABLE_JIT
        switch (action) {
-
        case MARSHAL_ACTION_CONV_IN: {
-
                if (t->attrs & PARAM_ATTRIBUTE_IN) {
 
                        /* Generates IL code for the following algorithm:
@@ -2848,7 +2948,6 @@ mono_cominterop_emit_marshal_safearray (EmitMarshalContext *m, int argnum, MonoT
                break;
 
        case MARSHAL_ACTION_CONV_OUT: {
-
                if (t->attrs & PARAM_ATTRIBUTE_OUT) {
                        /* Generates IL code for the following algorithm:
 
@@ -2966,6 +3065,7 @@ mono_cominterop_emit_marshal_safearray (EmitMarshalContext *m, int argnum, MonoT
        default:
                g_assert_not_reached ();
        }
+#endif /* DISABLE_JIT */
 
        return conv_arg;
 }
@@ -3060,13 +3160,15 @@ mono_marshal_safearray_begin (gpointer safearray, MonoArray **result, gpointer *
 
                                hr = mono_marshal_safe_array_get_lbound (safearray, i+1, &lbound);
                                if (hr < 0) {
-                                       cominterop_raise_hr_exception (hr);
+                                       cominterop_set_hr_error (&error, hr);
+                                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                                }
                                if (lbound != 0)
                                        bounded = TRUE;
                                hr = mono_marshal_safe_array_get_ubound (safearray, i+1, &ubound);
                                if (hr < 0) {
-                                       cominterop_raise_hr_exception (hr);
+                                       cominterop_set_hr_error (&error, hr);
+                                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                                }
                                cursize = ubound-lbound+1;
                                sizes [i] = cursize;
@@ -3093,17 +3195,20 @@ mono_marshal_safearray_begin (gpointer safearray, MonoArray **result, gpointer *
 static 
 gpointer mono_marshal_safearray_get_value (gpointer safearray, gpointer indices)
 {
+       MonoError error;
        gpointer result;
 #ifdef HOST_WIN32
        int hr = SafeArrayPtrOfIndex (safearray, indices, &result);
        if (hr < 0) {
-               cominterop_raise_hr_exception (hr);
+                       cominterop_set_hr_error (&error, hr);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
        }
 #else
        if (com_provider == MONO_COM_MS && init_com_provider_ms ()) {
                int hr = safe_array_ptr_of_index_ms (safearray, (glong *)indices, &result);
                if (hr < 0) {
-                       cominterop_raise_hr_exception (hr);
+                       cominterop_set_hr_error (&error, hr);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                }
        } else {
                g_assert_not_reached ();
@@ -3115,6 +3220,7 @@ gpointer mono_marshal_safearray_get_value (gpointer safearray, gpointer indices)
 static 
 gboolean mono_marshal_safearray_next (gpointer safearray, gpointer indices)
 {
+       MonoError error;
        int i;
        int dim = mono_marshal_safearray_get_dim (safearray);
        gboolean ret= TRUE;
@@ -3127,7 +3233,8 @@ gboolean mono_marshal_safearray_next (gpointer safearray, gpointer indices)
 
                hr = mono_marshal_safe_array_get_ubound (safearray, i+1, &ubound);
                if (hr < 0) {
-                       cominterop_raise_hr_exception (hr);
+                       cominterop_set_hr_error (&error, hr);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                }
 
                if (++pIndices[i] <= ubound) {
@@ -3136,7 +3243,8 @@ gboolean mono_marshal_safearray_next (gpointer safearray, gpointer indices)
 
                hr = mono_marshal_safe_array_get_lbound (safearray, i+1, &lbound);
                if (hr < 0) {
-                       cominterop_raise_hr_exception (hr);
+                       cominterop_set_hr_error (&error, hr);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                }
 
                pIndices[i] = lbound;
@@ -3211,15 +3319,19 @@ mono_marshal_safearray_create (MonoArray *input, gpointer *newsafearray, gpointe
 static 
 void mono_marshal_safearray_set_value (gpointer safearray, gpointer indices, gpointer value)
 {
+       MonoError error;
 #ifdef HOST_WIN32
        int hr = SafeArrayPutElement (safearray, indices, value);
-       if (hr < 0)
-               cominterop_raise_hr_exception (hr);
+       if (hr < 0) {
+               cominterop_set_hr_error (&error, hr);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
+       }
 #else
        if (com_provider == MONO_COM_MS && init_com_provider_ms ()) {
                int hr = safe_array_put_element_ms (safearray, (glong *)indices, (void **)value);
                if (hr < 0) {
-                       cominterop_raise_hr_exception (hr);
+                       cominterop_set_hr_error (&error, hr);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                }
        } else
                g_assert_not_reached ();
index fdca4871eebf02a17fed1a5501040909cdd56a28..54ee88204637c491d83ec9e7207404bba1aab863 100644 (file)
@@ -5,6 +5,7 @@
  *     Gonzalo Paniagua Javier (gonzalo@ximian.com)
  *
  * Copyright (c) 2005 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_CONSOLEIO_H
index 7c778bfacd14e66a927884e720d07a7d9bcd315f..b8367e888f7b851970cb4f7a2668558db116b90c 100644 (file)
@@ -5,6 +5,7 @@
  *     Gonzalo Paniagua Javier (gonzalo@ximian.com)
  *
  * Copyright (C) 2005-2009 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <mono/metadata/appdomain.h>
index fe59f700ea987d7a621daff20544b7808ec62acd..29ce37fc141bc4b8a92049e55590f10c7eef16b4 100644 (file)
@@ -5,6 +5,7 @@
  *     Gonzalo Paniagua Javier (gonzalo@ximian.com)
  *
  * Copyright (C) 2005-2009 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #if defined(__native_client__)
 #include "console-null.c"
@@ -254,7 +255,11 @@ do_console_cancel_event (void)
        method = mono_class_get_method_from_name (klass, "BeginInvoke", -1);
        g_assert (method != NULL);
 
-       mono_threadpool_ms_begin_invoke (domain, (MonoObject*) load_value, method, NULL);
+       mono_threadpool_ms_begin_invoke (domain, (MonoObject*) load_value, method, NULL, &error);
+       if (!is_ok (&error)) {
+               g_warning ("Couldn't invoke System.Console cancel handler due to %s", mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+       }
 }
 
 static int need_cancel = FALSE;
@@ -440,6 +445,8 @@ set_control_chars (MonoArray *control_chars, const guchar *cc)
 MonoBoolean
 ves_icall_System_ConsoleDriver_TtySetup (MonoString *keypad, MonoString *teardown, MonoArray **control_chars, int **size)
 {
+       MonoError error;
+
        int dims;
 
        dims = terminal_get_dimensions ();
@@ -465,7 +472,10 @@ ves_icall_System_ConsoleDriver_TtySetup (MonoString *keypad, MonoString *teardow
 
        /* 17 is the number of entries set in set_control_chars() above.
         * NCCS is the total size, but, by now, we only care about those 17 values*/
-       mono_gc_wbarrier_generic_store (control_chars, (MonoObject*) mono_array_new (mono_domain_get (), mono_defaults.byte_class, 17));
+       MonoArray *control_chars_arr = mono_array_new_checked (mono_domain_get (), mono_defaults.byte_class, 17, &error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
+       mono_gc_wbarrier_generic_store (control_chars, (MonoObject*) control_chars_arr);
        if (tcgetattr (STDIN_FILENO, &initial_attr) == -1)
                return FALSE;
 
index ff703808c3d9587a3cb6e7ed4a19b919e4cd1139..c7c8c49017b6182ee292e7d2d9fc373621384b22 100644 (file)
@@ -5,6 +5,7 @@
  *     Gonzalo Paniagua Javier (gonzalo@ximian.com)
  *
  * Copyright (C) 2005-2009 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index c2e47b9ca7b479a3a076a8db7c2f1694b2ac5212..326251cc140c53a575ff7e227abcdeea92bc2782 100644 (file)
@@ -5,6 +5,7 @@
  *   Kornel Pal <http://www.kornelpal.hu/>
  *
  * Copyright (C) 2008 Kornel Pal
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index a9c6a7cb76a750902db71952d766bb7a42aa15f8..ade821af5e316c1830aabb6e9096bf58a6179682 100644 (file)
@@ -5,6 +5,7 @@
  *   Kornel Pal <http://www.kornelpal.hu/>
  *
  * Copyright (C) 2008 Kornel Pal
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_COREE_H__
index 2553361c14db27d1af028b583ffbf1848b13c6a6..baf79f6be9709502aa442df5fe76f9570e73719a 100644 (file)
@@ -5,6 +5,7 @@
  *     Mono Project (http://www.mono-project.com)
  *
  * Copyright (C) 2005-2008 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <string.h>
index fcbfd9d817f06daf4acc5c25b57d23c1923237e6..e6d9cc95e2f578977f80362f5ce971b5ef15c42e 100644 (file)
@@ -7,6 +7,7 @@
  *     Mono Project (http://www.mono-project.com)
  *
  * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index e23b279cd94007bf047878082857aaa09e0da49c..decf5e8d04bdf27eff3b5d5f887f9f8644b049f6 100644 (file)
@@ -7,6 +7,7 @@
  *     Mono Project (http://www.mono-project.com)
  *
  * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_METADATA_DEBUG_MONO_PPDB_H__
index 8df4c0f902606edc04b31b5b97cb1350b851482d..f418b2078cee4af6f2da49eb191d887c99d458bb 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright (C) 2005-2008 Novell, Inc. (http://www.novell.com)
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 684168994b43e3f6952476f075fa02a230fea3f7..3b3459f32587e13e2589a4d0d1f3d7dbe12aa99a 100644 (file)
@@ -2,6 +2,7 @@
  * This header is only installed for use by the debugger:
  * the structures and the API declared here are not supported.
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_DEBUG_MONO_SYMFILE_H__
index dfd65e48a211a1b8e8094a7340dce36921618cb5..5e3adb36a48537df661e036429f35b7b745af26a 100644 (file)
@@ -1,6 +1,7 @@
 /*
  * Appdomain-related internal data structures and functions.
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_METADATA_DOMAIN_INTERNALS_H__
 #define __MONO_METADATA_DOMAIN_INTERNALS_H__
index ab021003394f58b85d425213a51cff84e4afa042..fa2514b9814b088d8748494a51fda80edc8c2df3 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011-2012 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -782,7 +783,7 @@ mono_init_internal (const char *filename, const char *exe_filename, const char *
 
        mono_assembly_load_friends (ass);
 
-       mono_defaults.handleref_class = mono_class_load_from_name (
+       mono_defaults.handleref_class = mono_class_try_load_from_name (
                mono_defaults.corlib, "System.Runtime.InteropServices", "HandleRef");
 
        mono_defaults.attribute_class = mono_class_load_from_name (
@@ -1168,12 +1169,6 @@ mono_domain_free (MonoDomain *domain, gboolean force)
        g_slist_free (domain->domain_assemblies);
        domain->domain_assemblies = NULL;
 
-       /* 
-        * Send this after the assemblies have been unloaded and the domain is still in a 
-        * usable state.
-        */
-       mono_profiler_appdomain_event (domain, MONO_PROFILE_END_UNLOAD);
-
        if (free_domain_hook)
                free_domain_hook (domain);
 
index e0d1970f61279e87374354b4bc734610cd344c9d..4726f9ba703db888ea33078bd842e31ccb88e294 100644 (file)
@@ -7,6 +7,7 @@
  *
  * Copyright 2002-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index cdf5ea0965e97c2a795733944fb8f81d9f73ad75..e2e162f702a1efeb69e0226a5a4ab8eedb4d52d4 100644 (file)
@@ -9,6 +9,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <glib.h>
@@ -939,8 +940,10 @@ ves_icall_Mono_Runtime_GetNativeStackTrace (MonoException *exc)
 {
        char *trace;
        MonoString *res;
-       if (!exc)
-               mono_raise_exception (mono_get_exception_argument_null ("exception"));
+       if (!exc) {
+               mono_set_pending_exception (mono_get_exception_argument_null ("exception"));
+               return NULL;
+       }
 
        trace = mono_exception_get_native_backtrace (exc);
        res = mono_string_new (mono_domain_get (), trace);
@@ -966,11 +969,27 @@ mono_error_raise_exception (MonoError *target_error)
                mono_raise_exception (ex);
 }
 
-void
+/**
+ * mono_error_set_pending_exception:
+ * @error: The error
+ *
+ *
+ * If @error is set, convert it to an exception and set the pending exception for the current icall.
+ * Returns TRUE if @error was set, or FALSE otherwise, so that you can write:
+ *    if (mono_error_set_pending_exception (error)) {
+ *      { ... cleanup code ... }
+ *      return;
+ *    }
+ */
+gboolean
 mono_error_set_pending_exception (MonoError *error)
 {
        MonoException *ex = mono_error_convert_to_exception (error);
-       if (ex)
+       if (ex) {
                mono_set_pending_exception (ex);
+               return TRUE;
+       } else {
+               return FALSE;
+       }
 }
 
index 71a956679d11c43faf1cc86b7264b1dbacfb09ef..c10b1fee8d934b8249c8ca70b32497e0c5a174dc 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -393,31 +394,38 @@ MonoArray *
 ves_icall_System_IO_MonoIO_GetFileSystemEntries (MonoString *path,
                                                 MonoString *path_with_pattern,
                                                 gint attrs, gint mask,
-                                                gint32 *error)
+                                                gint32 *ioerror)
 {
+       MonoError error;
        MonoDomain *domain = mono_domain_get ();
        MonoArray *result;
        int i;
        GPtrArray *names;
        
-       *error = ERROR_SUCCESS;
+       *ioerror = ERROR_SUCCESS;
 
        MONO_PREPARE_BLOCKING;
-       names = get_filesystem_entries (mono_string_chars (path), mono_string_chars (path_with_pattern), attrs, mask, error);
+       names = get_filesystem_entries (mono_string_chars (path), mono_string_chars (path_with_pattern), attrs, mask, ioerror);
        MONO_FINISH_BLOCKING;
 
        if (!names) {
                // If there's no array and no error, then return an empty array.
-               if (*error == ERROR_SUCCESS)
-                       return mono_array_new (domain, mono_defaults.string_class, 0);
+               if (*ioerror == ERROR_SUCCESS) {
+                       MonoArray *arr = mono_array_new_checked (domain, mono_defaults.string_class, 0, &error);
+                       mono_error_set_pending_exception (&error);
+                       return arr;
+               }
                return NULL;
        }
 
-       result = mono_array_new (domain, mono_defaults.string_class, names->len);
+       result = mono_array_new_checked (domain, mono_defaults.string_class, names->len, &error);
+       if (mono_error_set_pending_exception (&error))
+               goto leave;
        for (i = 0; i < names->len; i++) {
                mono_array_setref (result, i, mono_string_new (domain, (const char *)g_ptr_array_index (names, i)));
                g_free (g_ptr_array_index (names, i));
        }
+leave:
        g_ptr_array_free (names, TRUE);
        return result;
 }
@@ -569,7 +577,7 @@ ves_icall_System_IO_MonoIO_GetCurrentDirectory (gint32 *io_error)
        }
 
        g_free (buf);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -1167,13 +1175,16 @@ invalid_path_chars [] = {
 MonoArray *
 ves_icall_System_IO_MonoIO_get_InvalidPathChars ()
 {
+       MonoError error;
        MonoArray *chars;
        MonoDomain *domain;
        int i, n;
 
        domain = mono_domain_get ();
        n = sizeof (invalid_path_chars) / sizeof (gunichar2);
-       chars = mono_array_new (domain, mono_defaults.char_class, n);
+       chars = mono_array_new_checked (domain, mono_defaults.char_class, n, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        for (i = 0; i < n; ++ i)
                mono_array_set (chars, gunichar2, i, invalid_path_chars [i]);
index 2974bd49949ecdd27de60df557c33ee102df61e4..ab10f929173b4413ac188294374ce56a9447406d 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2001 Ximian, Inc.
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_FILEIO_H_
index aca3e7fb49c6fab2a7f25c8b89aeca79d801763e..efa5547f6e485fa3a5f81522dc9fddc2153194c9 100644 (file)
@@ -5,6 +5,7 @@
  *     Rodrigo Kumpera
  *
  * Copyright 2014 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 56d598ee7f21523345f5187b5f8e09cf00eab753..dba37472c34741355a3f5e1e954f4c54a86801ad 100644 (file)
@@ -5,6 +5,7 @@
  *     Rodrigo Kumpera
  *
  * Copyright 2014 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 0e391ff1d4016bbbafdb0be16c3c67616aa8bddd..cef862e3bea755408ad986fcafb3f19d87b99cd4 100644 (file)
@@ -5,6 +5,7 @@
  *     Rodrigo Kumpera
  *
  * Copyright 2014 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_FILE_MMAP_H_
index def11d9856d8be929b37c1fc92f0c48651ca4dd4..eb1827a0c6055f863341ad2c12cdcf55b11ec600 100644 (file)
@@ -5,6 +5,7 @@
  *     Gonzalo Paniagua Javier (gonzalo@ximian.com)
  *
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifdef HAVE_CONFIG_H
index bc13b1ea2694af528adf30c07927aaea3481d01b..52d950d8cca7b8469db99a3f95dcd751d6a24f4b 100644 (file)
@@ -5,6 +5,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_METADATA_GC_INTERNAL_H__
index ff442e43f6a7faf3484ec2848e7d0bc01d0f6438..ef232a93e5e98a27911de3bb57996cdb9a5b683f 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/sgen/gc-internal-agnostic.h"
index 077251c7b1e7b95e0ec13895562a79111a735f90..2cff646db1771c099780ffccbf618800d049a270 100644 (file)
@@ -6,6 +6,7 @@
  * Copyright 2002-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -39,6 +40,7 @@
 #include <mono/utils/mono-threads.h>
 #include <mono/utils/atomic.h>
 #include <mono/utils/mono-coop-semaphore.h>
+#include <mono/utils/hazard-pointer.h>
 
 #ifndef HOST_WIN32
 #include <pthread.h>
@@ -451,6 +453,8 @@ mono_domain_finalize (MonoDomain *domain, guint32 timeout)
                mono_gc_finalize_threadpool_threads ();
        }
 
+       mono_profiler_appdomain_event (domain, MONO_PROFILE_END_UNLOAD);
+
        return TRUE;
 }
 
@@ -638,6 +642,41 @@ mono_gc_finalize_notify (void)
        mono_coop_sem_post (&finalizer_sem);
 }
 
+/*
+This is the number of entries allowed in the hazard free queue before
+we explicitly cycle the finalizer thread to trigger pumping the queue.
+
+It was picked empirically by running the corlib test suite in a stress
+scenario where all hazard entries are queued.
+
+In this extreme scenario we double the number of times we cycle the finalizer
+thread compared to just GC calls.
+
+Entries are usually in the order of 100's of bytes each, so we're limiting
+floating garbage to be in the order of a dozen kb.
+*/
+static gboolean finalizer_thread_pulsed;
+#define HAZARD_QUEUE_OVERFLOW_SIZE 20
+
+static void
+hazard_free_queue_is_too_big (size_t size)
+{
+       if (size < HAZARD_QUEUE_OVERFLOW_SIZE)
+               return;
+
+       if (finalizer_thread_pulsed || InterlockedCompareExchange (&finalizer_thread_pulsed, TRUE, FALSE))
+               return;
+
+       mono_gc_finalize_notify ();
+}
+
+static void
+hazard_free_queue_pump (void)
+{
+       mono_thread_hazardous_try_free_all ();
+       finalizer_thread_pulsed = FALSE;
+}
+
 #ifdef HAVE_BOEHM_GC
 
 static void
@@ -711,8 +750,15 @@ finalize_domain_objects (DomainFinalizationReq *req)
 static guint32
 finalizer_thread (gpointer unused)
 {
+       MonoError error;
+       mono_thread_set_name_internal (mono_thread_internal_current (), mono_string_new (mono_get_root_domain (), "Finalizer"), FALSE, &error);
+       mono_error_assert_ok (&error);
+
        gboolean wait = TRUE;
 
+       /* Register a hazard free queue pump callback */
+       mono_hazard_pointer_install_free_queue_size_callback (hazard_free_queue_is_too_big);
+
        while (!finished) {
                /* Wait to be notified that there's at least one
                 * finaliser to run
@@ -757,6 +803,8 @@ finalizer_thread (gpointer unused)
 
                reference_queue_proccess_all ();
 
+               hazard_free_queue_pump ();
+
                /* Avoid posting the pending done event until there are pending finalizers */
                if (mono_coop_sem_timedwait (&finalizer_sem, 0, MONO_SEM_FLAGS_NONE) == 0) {
                        /* Don't wait again at the start of the loop */
@@ -780,8 +828,9 @@ static
 void
 mono_gc_init_finalizer_thread (void)
 {
-       gc_thread = mono_thread_create_internal (mono_domain_get (), finalizer_thread, NULL, FALSE, 0);
-       ves_icall_System_Threading_Thread_SetName_internal (gc_thread, mono_string_new (mono_domain_get (), "Finalizer"));
+       MonoError error;
+       gc_thread = mono_thread_create_internal (mono_domain_get (), finalizer_thread, NULL, FALSE, 0, &error);
+       mono_error_assert_ok (&error);
 }
 
 void
index c962bda7c7fb59bdc0d8c25b7b2dec5bdf82cc78..6c266259508ae6f251856794587f9967db5fd7b1 100644 (file)
@@ -5,6 +5,7 @@
  *  - Ludovic Henry <ludovic@xamarin.com>
  *
  * Copyright 2015 Xamarin, Inc. (www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index b933039b0b0ed222b08aaa2df015b7f947e13b04..99a0428290355f98fad465166ced168e0b8f1c84 100644 (file)
@@ -5,6 +5,7 @@
  *  - Ludovic Henry <ludovic@xamarin.com>
  *
  * Copyright 2015 Xamarin, Inc. (www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_HANDLE_H__
@@ -94,7 +95,7 @@ mono_handle_elevate (MonoHandle handle)
        return mono_handle_arena_elevate (mono_handle_arena_current (), handle);
 }
 
-#ifndef CHECKED_BUILD
+#ifndef ENABLE_CHECKED_BUILD
 
 #define mono_handle_obj(handle) ((handle)->__private_obj)
 
index 6f82e40d54868e976179b1c19ae63009d8b06e88..b74631fd9420a19a216568a45eb1d0c00380a785 100644 (file)
@@ -104,7 +104,7 @@ ICALL(ARGI_4, "Setup",                            mono_ArgIterator_Setup)
 
 ICALL_TYPE(ARRAY, "System.Array", ARRAY_1)
 ICALL(ARRAY_1, "ClearInternal",    ves_icall_System_Array_ClearInternal)
-ICALL(ARRAY_2, "Clone",            mono_array_clone)
+ICALL(ARRAY_2, "Clone",            ves_icall_System_Array_Clone)
 ICALL(ARRAY_3, "CreateInstanceImpl",   ves_icall_System_Array_CreateInstanceImpl)
 ICALL(ARRAY_14, "CreateInstanceImpl64",   ves_icall_System_Array_CreateInstanceImpl64)
 ICALL(ARRAY_4, "FastCopy",         ves_icall_System_Array_FastCopy)
@@ -210,9 +210,6 @@ ICALL(PROCESS_10, "ProcessName_internal(intptr)", ves_icall_System_Diagnostics_P
 ICALL(PROCESS_13, "ShellExecuteEx_internal(System.Diagnostics.ProcessStartInfo,System.Diagnostics.Process/ProcInfo&)", ves_icall_System_Diagnostics_Process_ShellExecuteEx_internal)
 #endif /* !DISABLE_PROCESS_HANDLING */
 
-ICALL_TYPE(SFRAME, "System.Diagnostics.StackFrame", SFRAME_1)
-ICALL(SFRAME_1, "GetILOffsetFromFile", ves_icall_System_StackFrame_GetILOffsetFromFile)
-
 ICALL_TYPE(STOPWATCH, "System.Diagnostics.Stopwatch", STOPWATCH_1)
 ICALL(STOPWATCH_1, "GetTimestamp", mono_100ns_ticks)
 
@@ -227,7 +224,7 @@ ICALL(ENUM_7, "get_value", ves_icall_System_Enum_get_value)
 
 ICALL_TYPE(ENV, "System.Environment", ENV_1)
 ICALL(ENV_1, "Exit", ves_icall_System_Environment_Exit)
-ICALL(ENV_2, "GetCommandLineArgs", mono_runtime_get_main_args)
+ICALL(ENV_2, "GetCommandLineArgs", ves_icall_System_Environment_GetCoomandLineArgs)
 ICALL(ENV_3, "GetEnvironmentVariableNames", ves_icall_System_Environment_GetEnvironmentVariableNames)
 ICALL(ENV_31, "GetIs64BitOperatingSystem", ves_icall_System_Environment_GetIs64BitOperatingSystem)
 ICALL(ENV_4, "GetLogicalDrivesInternal", ves_icall_System_Environment_GetLogicalDrives )
@@ -496,18 +493,15 @@ ICALL(ASSEMN_1, "ParseName", ves_icall_System_Reflection_AssemblyName_ParseName)
 ICALL(ASSEMN_2, "get_public_token", mono_digest_get_public_token)
 
 ICALL_TYPE(CATTR_DATA, "System.Reflection.CustomAttributeData", CATTR_DATA_1)
-ICALL(CATTR_DATA_1, "ResolveArgumentsInternal", mono_reflection_resolve_custom_attribute_data)
+ICALL(CATTR_DATA_1, "ResolveArgumentsInternal", ves_icall_System_Reflection_CustomAttributeData_ResolveArgumentsInternal)
 
 ICALL_TYPE(ASSEMB, "System.Reflection.Emit.AssemblyBuilder", ASSEMB_1)
 ICALL(ASSEMB_1, "InternalAddModule", ves_icall_System_Reflection_Emit_AssemblyBuilder_InternalAddModule)
 ICALL(ASSEMB_2, "basic_init", mono_image_basic_init)
 
-ICALL_TYPE(CATTRB, "System.Reflection.Emit.CustomAttributeBuilder", CATTRB_1)
-ICALL(CATTRB_1, "GetBlob", mono_reflection_get_custom_attrs_blob)
-
 #ifndef DISABLE_REFLECTION_EMIT
-ICALL_TYPE(DERIVEDTYPE, "System.Reflection.Emit.DerivedType", DERIVEDTYPE_1)
-ICALL(DERIVEDTYPE_1, "create_unmanaged_type", mono_reflection_create_unmanaged_type)
+ICALL_TYPE(CATTRB, "System.Reflection.Emit.CustomAttributeBuilder", CATTRB_1)
+ICALL(CATTRB_1, "GetBlob", ves_icall_System_Reflection_Emit_CustomAttributeBuilder_GetBlob)
 #endif
 
 ICALL_TYPE(DYNM, "System.Reflection.Emit.DynamicMethod", DYNM_1)
@@ -538,8 +532,13 @@ ICALL_TYPE(SIGH, "System.Reflection.Emit.SignatureHelper", SIGH_1)
 ICALL(SIGH_1, "get_signature_field", mono_reflection_sighelper_get_signature_field)
 ICALL(SIGH_2, "get_signature_local", mono_reflection_sighelper_get_signature_local)
 
+#ifndef DISABLE_REFLECTION_EMIT
+ICALL_TYPE(SYMBOLTYPE, "System.Reflection.Emit.SymbolType", SYMBOLTYPE_1)
+ICALL(SYMBOLTYPE_1, "create_unmanaged_type", mono_reflection_create_unmanaged_type)
+#endif
+
 ICALL_TYPE(TYPEB, "System.Reflection.Emit.TypeBuilder", TYPEB_1)
-ICALL(TYPEB_1, "create_generic_class", mono_reflection_create_generic_class)
+ICALL(TYPEB_1, "create_generic_class", ves_icall_System_Reflection_Emit_TypeBuilder_create_generic_class)
 ICALL(TYPEB_2, "create_internal_class", mono_reflection_create_internal_class)
 ICALL(TYPEB_3, "create_runtime_class", mono_reflection_create_runtime_class)
 ICALL(TYPEB_4, "get_IsGenericParameter", ves_icall_TypeBuilder_get_IsGenericParameter)
@@ -579,6 +578,7 @@ ICALL(MODULE_13, "get_MetadataToken", ves_icall_reflection_get_token)
 ICALL_TYPE(MCMETH, "System.Reflection.MonoCMethod", MCMETH_1)
 ICALL(MCMETH_1, "GetGenericMethodDefinition_impl", ves_icall_MonoMethod_GetGenericMethodDefinition)
 ICALL(MCMETH_2, "InternalInvoke", ves_icall_InternalInvoke)
+ICALL(MCMETH_3, "get_core_clr_security_level", ves_icall_MonoMethod_get_core_clr_security_level)
 
 ICALL_TYPE(MEVIN, "System.Reflection.MonoEventInfo", MEVIN_1)
 ICALL(MEVIN_1, "get_event_info", ves_icall_MonoEventInfo_get_event_info)
index 49bd4482155f96b6d9149f7c51a2a77a54fb2fba..e22c730342dc4a3bc8eadcb4932aa9722ad5cc93 100644 (file)
@@ -11,6 +11,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011-2015 Xamarin Inc (http://www.xamarin.com).
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -138,19 +139,23 @@ mono_class_init_checked (MonoClass *klass, MonoError *error)
 ICALL_EXPORT MonoObject *
 ves_icall_System_Array_GetValueImpl (MonoArray *arr, guint32 pos)
 {
+       MonoError error;
        MonoClass *ac;
        gint32 esize;
        gpointer *ea;
+       MonoObject *result = NULL;
 
        ac = (MonoClass *)arr->obj.vtable->klass;
 
        esize = mono_array_element_size (ac);
        ea = (gpointer*)((char*)arr->vector + (pos * esize));
 
-       if (ac->element_class->valuetype)
-               return mono_value_box (arr->obj.vtable->domain, ac->element_class, ea);
-       else
-               return (MonoObject *)*ea;
+       if (ac->element_class->valuetype) {
+               result = mono_value_box_checked (arr->obj.vtable->domain, ac->element_class, ea, &error);
+               mono_error_set_pending_exception (&error);
+       } else
+               result = (MonoObject *)*ea;
+       return result;
 }
 
 ICALL_EXPORT MonoObject *
@@ -203,6 +208,7 @@ ves_icall_System_Array_GetValue (MonoArray *arr, MonoArray *idxs)
 ICALL_EXPORT void
 ves_icall_System_Array_SetValueImpl (MonoArray *arr, MonoObject *value, guint32 pos)
 {
+       MonoError error;
        MonoClass *ac, *vc, *ec;
        gint32 esize, vsize;
        gpointer *ea, *va;
@@ -212,6 +218,8 @@ ves_icall_System_Array_SetValueImpl (MonoArray *arr, MonoObject *value, guint32
        gint64 i64 = 0;
        gdouble r64 = 0;
 
+       mono_error_init (&error);
+
        if (value)
                vc = value->vtable->klass;
        else
@@ -289,19 +297,24 @@ ves_icall_System_Array_SetValueImpl (MonoArray *arr, MonoObject *value, guint32
        }
 
        if (!ec->valuetype) {
-               if (!mono_object_isinst (value, ec))
+               gboolean castOk = (NULL != mono_object_isinst_checked (value, ec, &error));
+               if (mono_error_set_pending_exception (&error))
+                       return;
+               if (!castOk)
                        INVALID_CAST;
                mono_gc_wbarrier_set_arrayref (arr, ea, (MonoObject*)value);
                return;
        }
 
-       if (mono_object_isinst (value, ec)) {
+       if (mono_object_isinst_checked (value, ec, &error)) {
                if (ec->has_references)
                        mono_value_copy (ea, (char*)value + sizeof (MonoObject), ec);
                else
                        mono_gc_memmove_atomic (ea, (char *)value + sizeof (MonoObject), esize);
                return;
        }
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        if (!vc->valuetype)
                INVALID_CAST;
@@ -552,7 +565,8 @@ ves_icall_System_Array_CreateInstanceImpl (MonoReflectionType *type, MonoArray *
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (bounds && (mono_array_length (bounds) == 1) && (mono_array_get (bounds, gint32, 0) != 0))
                /* vectors are not the same as one dimensional arrays with no-zero bounds */
@@ -603,7 +617,8 @@ ves_icall_System_Array_CreateInstanceImpl64 (MonoReflectionType *type, MonoArray
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (bounds && (mono_array_length (bounds) == 1) && (mono_array_get (bounds, gint64, 0) != 0))
                /* vectors are not the same as one dimensional arrays with no-zero bounds */
@@ -698,6 +713,15 @@ ves_icall_System_Array_ClearInternal (MonoArray *arr, int idx, int length)
        mono_gc_bzero_atomic (mono_array_addr_with_size_fast (arr, sz, idx), length * sz);
 }
 
+ICALL_EXPORT MonoArray*
+ves_icall_System_Array_Clone (MonoArray *arr)
+{
+       MonoError error;
+       MonoArray *result = mono_array_clone_checked (arr, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
 ICALL_EXPORT gboolean
 ves_icall_System_Array_FastCopy (MonoArray *source, int source_idx, MonoArray* dest, int dest_idx, int length)
 {
@@ -1036,7 +1060,10 @@ ves_icall_System_ValueType_InternalGetHashCode (MonoObject *this_obj, MonoArray
 
        if (values) {
                int i;
-               mono_gc_wbarrier_generic_store (fields, (MonoObject*) mono_array_new (mono_domain_get (), mono_defaults.object_class, count));
+               MonoArray *fields_arr = mono_array_new_checked (mono_domain_get (), mono_defaults.object_class, count, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return 0;
+               mono_gc_wbarrier_generic_store (fields, (MonoObject*) fields_arr);
                for (i = 0; i < count; ++i)
                        mono_array_setref (*fields, i, values [i]);
        } else {
@@ -1155,7 +1182,10 @@ ves_icall_System_ValueType_Equals (MonoObject *this_obj, MonoObject *that, MonoA
 
        if (values) {
                int i;
-               mono_gc_wbarrier_generic_store (fields, (MonoObject*) mono_array_new (mono_domain_get (), mono_defaults.object_class, count));
+               MonoArray *fields_arr = mono_array_new_checked (mono_domain_get (), mono_defaults.object_class, count, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return FALSE;
+               mono_gc_wbarrier_generic_store (fields, (MonoObject*) fields_arr);
                for (i = 0; i < count; ++i)
                        mono_array_setref_fast (*fields, i, values [i]);
                return FALSE;
@@ -1176,8 +1206,7 @@ ves_icall_System_Object_GetType (MonoObject *obj)
 #endif
                ret = mono_type_get_object_checked (mono_object_domain (obj), &obj->vtable->klass->byval_arg, &error);
 
-       mono_error_raise_exception (&error);
-
+       mono_error_set_pending_exception (&error);
        return ret;
 }
 
@@ -1195,7 +1224,7 @@ ves_icall_ModuleBuilder_getToken (MonoReflectionModuleBuilder *mb, MonoObject *o
        
        MonoError error;
        gint32 result = mono_image_create_token (mb->dynamic_image, obj, create_open_instance, TRUE, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -1209,7 +1238,7 @@ ves_icall_ModuleBuilder_getMethodToken (MonoReflectionModuleBuilder *mb,
        MonoError error;
        gint32 result = mono_image_create_method_token (
                mb->dynamic_image, (MonoObject *) method, opt_param_types, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -1218,15 +1247,15 @@ ves_icall_ModuleBuilder_WriteToFile (MonoReflectionModuleBuilder *mb, HANDLE fil
 {
        MonoError error;
        mono_image_create_pefile (mb, file, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 }
 
 ICALL_EXPORT void
 ves_icall_ModuleBuilder_build_metadata (MonoReflectionModuleBuilder *mb)
 {
        MonoError error;
-       if (!mono_image_build_metadata (mb, &error))
-               mono_error_raise_exception (&error);
+       mono_image_build_metadata (mb, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 ICALL_EXPORT void
@@ -1256,8 +1285,34 @@ ves_icall_System_Reflection_Emit_AssemblyBuilder_InternalAddModule (MonoReflecti
        return result;
 }
 
+/**
+ * ves_icall_System_Reflection_Emit_TypeBuilder_create_generic_class:
+ * @tb: a TypeBuilder object
+ *
+ * (icall)
+ * Creates the generic class after all generic parameters have been added.
+ */
+ICALL_EXPORT void
+ves_icall_System_Reflection_Emit_TypeBuilder_create_generic_class (MonoReflectionTypeBuilder *tb)
+{
+       MonoError error;
+       (void) mono_reflection_create_generic_class (tb, &error);
+       mono_error_set_pending_exception (&error);
+}
+
+#ifndef DISABLE_REFLECTION_EMIT
+ICALL_EXPORT MonoArray*
+ves_icall_System_Reflection_Emit_CustomAttributeBuilder_GetBlob (MonoReflectionAssembly *assembly, MonoObject *ctor, MonoArray *ctorArgs, MonoArray *properties, MonoArray *propValues, MonoArray *fields, MonoArray* fieldValues)
+{
+       MonoError error;
+       MonoArray *result = mono_reflection_get_custom_attrs_blob_checked (assembly, ctor, ctorArgs, properties, propValues, fields, fieldValues, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+#endif
+
 static gboolean
-get_caller (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
+get_executing (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
 {
        MonoMethod **dest = (MonoMethod **)data;
 
@@ -1265,11 +1320,9 @@ get_caller (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer dat
        if (!managed)
                return FALSE;
 
-       if (m == *dest) {
-               *dest = NULL;
-               return FALSE;
-       }
        if (!(*dest)) {
+               if (!strcmp (m->klass->name_space, "System.Reflection"))
+                       return FALSE;
                *dest = m;
                return TRUE;
        }
@@ -1277,7 +1330,7 @@ get_caller (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer dat
 }
 
 static gboolean
-get_executing (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
+get_caller_no_reflection (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
 {
        MonoMethod **dest = (MonoMethod **)data;
 
@@ -1285,9 +1338,18 @@ get_executing (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer
        if (!managed)
                return FALSE;
 
+       if (m->wrapper_type != MONO_WRAPPER_NONE)
+               return FALSE;
+
+       if (m == *dest) {
+               *dest = NULL;
+               return FALSE;
+       }
+
+       if (m->klass->image == mono_defaults.corlib && !strcmp (m->klass->name_space, "System.Reflection"))
+               return FALSE;
+
        if (!(*dest)) {
-               if (!strcmp (m->klass->name_space, "System.Reflection"))
-                       return FALSE;
                *dest = m;
                return TRUE;
        }
@@ -1295,7 +1357,7 @@ get_executing (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer
 }
 
 static gboolean
-get_caller_no_reflection (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
+get_caller_no_system_or_reflection (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed, gpointer data)
 {
        MonoMethod **dest = (MonoMethod **)data;
 
@@ -1306,13 +1368,15 @@ get_caller_no_reflection (MonoMethod *m, gint32 no, gint32 ilo, gboolean managed
        if (m->wrapper_type != MONO_WRAPPER_NONE)
                return FALSE;
 
-       if (m->klass->image == mono_defaults.corlib && !strcmp (m->klass->name_space, "System.Reflection"))
-               return FALSE;
-
        if (m == *dest) {
                *dest = NULL;
                return FALSE;
        }
+
+       if (m->klass->image == mono_defaults.corlib && ((!strcmp (m->klass->name_space, "System.Reflection"))
+                                                                                                       || (!strcmp (m->klass->name_space, "System"))))
+               return FALSE;
+
        if (!(*dest)) {
                *dest = m;
                return TRUE;
@@ -1328,6 +1392,7 @@ type_from_parsed_name (MonoTypeNameParse *info, MonoBoolean ignoreCase, MonoErro
        MonoType *type = NULL;
        MonoAssembly *assembly = NULL;
        gboolean type_resolve = FALSE;
+       MonoImage *rootimage = NULL;
 
        mono_error_init (error);
 
@@ -1338,10 +1403,23 @@ type_from_parsed_name (MonoTypeNameParse *info, MonoBoolean ignoreCase, MonoErro
         */
        m = mono_method_get_last_managed ();
        dest = m;
-
-       mono_stack_walk_no_il (get_caller_no_reflection, &dest);
-       if (!dest)
-               dest = m;
+       if (m && m->klass->image != mono_defaults.corlib) {
+               /* Happens with inlining */
+       } else {
+               /* Ugly hack: type_from_parsed_name is called from
+                * System.Type.internal_from_name, which is called most
+                * directly from System.Type.GetType(string,bool,bool) but
+                * also indirectly from places such as
+                * System.Type.GetType(string,func,func) (via
+                * System.TypeNameParser.GetType and System.TypeSpec.Resolve)
+                * so we need to skip over all of those to find the true caller.
+                *
+                * It would be nice if we had stack marks.
+                */
+               mono_stack_walk_no_il (get_caller_no_system_or_reflection, &dest);
+               if (!dest)
+                       dest = m;
+       }
 
        /*
         * FIXME: mono_method_get_last_managed() sometimes returns NULL, thus
@@ -1354,6 +1432,7 @@ type_from_parsed_name (MonoTypeNameParse *info, MonoBoolean ignoreCase, MonoErro
        if (dest) {
                assembly = dest->klass->image->assembly;
                type_resolve = TRUE;
+               rootimage = assembly->image;
        } else {
                g_warning (G_STRLOC);
        }
@@ -1361,21 +1440,28 @@ type_from_parsed_name (MonoTypeNameParse *info, MonoBoolean ignoreCase, MonoErro
        if (info->assembly.name)
                assembly = mono_assembly_load (&info->assembly, assembly ? assembly->basedir : NULL, NULL);
 
-
        if (assembly) {
                /* When loading from the current assembly, AppDomain.TypeResolve will not be called yet */
-               type = mono_reflection_get_type_checked (assembly->image, info, ignoreCase, &type_resolve, error);
+               type = mono_reflection_get_type_checked (rootimage, assembly->image, info, ignoreCase, &type_resolve, error);
                return_val_if_nok (error, NULL);
        }
 
+       // XXXX - aleksey -
+       //  Say we're looking for System.Generic.Dict<int, Local>
+       //  we FAIL the get type above, because S.G.Dict isn't in assembly->image.  So we drop down here.
+       //  but then we FAIL AGAIN because now we pass null as the image and the rootimage and everything
+       //  is messed up when we go to construct the Local as the type arg...
+       //
+       // By contrast, if we started with Mine<System.Generic.Dict<int, Local>> we'd go in with assembly->image
+       // as the root and then even the detour into generics would still not screw us when we went to load Local.
        if (!info->assembly.name && !type) {
                /* try mscorlib */
-               type = mono_reflection_get_type_checked (NULL, info, ignoreCase, &type_resolve, error);
+               type = mono_reflection_get_type_checked (rootimage, NULL, info, ignoreCase, &type_resolve, error);
                return_val_if_nok (error, NULL);
        }
        if (assembly && !type && type_resolve) {
                type_resolve = FALSE; /* This will invoke TypeResolve if not done in the first 'if' */
-               type = mono_reflection_get_type_checked (assembly->image, info, ignoreCase, &type_resolve, error);
+               type = mono_reflection_get_type_checked (rootimage, assembly->image, info, ignoreCase, &type_resolve, error);
                return_val_if_nok (error, NULL);
        }
 
@@ -1401,10 +1487,12 @@ ves_icall_System_Type_internal_from_name (MonoString *name,
        /* mono_reflection_parse_type() mangles the string */
        if (!parsedOk) {
                mono_reflection_free_type_info (&info);
-               g_free (str);
                if (throwOnError) {
-                       mono_set_pending_exception (mono_get_exception_argument("typeName", "failed parse"));
+                       mono_error_init (&error);
+                       mono_error_set_argument (&error, "typeName", "failed parse: %s", str);
+                       mono_error_set_pending_exception (&error);
                }
+               g_free (str);
                return NULL;
        }
 
@@ -1427,7 +1515,6 @@ ves_icall_System_Type_internal_from_name (MonoString *name,
                if (throwOnError)
                        e = mono_get_exception_type_load (name, NULL);
 
-               mono_loader_clear_error ();
                if (e) {
                        mono_set_pending_exception (e);
                        return NULL;
@@ -1446,7 +1533,7 @@ ves_icall_System_Type_internal_from_handle (MonoType *handle)
        MonoDomain *domain = mono_domain_get (); 
 
        ret = mono_type_get_object_checked (domain, handle, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -1617,8 +1704,13 @@ ves_icall_RuntimeTypeHandle_IsInstanceOfType (MonoReflectionType *type, MonoObje
        MonoError error;
        MonoClass *klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
-       return mono_object_isinst (obj, klass) != NULL;
+       if (!is_ok (&error)) {
+               mono_error_set_pending_exception (&error);
+               return FALSE;
+       }
+       guint32 result = (mono_object_isinst_checked (obj, klass, &error) != NULL);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 ICALL_EXPORT guint32
@@ -1693,7 +1785,7 @@ ves_icall_System_Reflection_FieldInfo_internal_from_handle_type (MonoClassField
        }
 
        MonoReflectionField *result = mono_field_get_object_checked (mono_domain_get (), klass, handle, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -1710,7 +1802,7 @@ ves_icall_System_Reflection_FieldInfo_GetTypeModifiers (MonoReflectionField *fie
        }
 
        res = type_array_from_modifiers (field->field->parent->image, type, optional, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -1823,7 +1915,7 @@ ves_icall_MonoField_GetParentType (MonoReflectionField *field, MonoBoolean decla
        parent = declaring? field->field->parent: field->klass;
 
        ret = mono_type_get_object_checked (mono_object_domain (field), &parent->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 
@@ -1843,8 +1935,11 @@ ves_icall_MonoField_GetValueInternal (MonoReflectionField *field, MonoObject *ob
                return NULL;
        }
 
-       if (mono_security_core_clr_enabled ())
-               mono_security_core_clr_ensure_reflection_access_field (cf);
+       if (mono_security_core_clr_enabled () &&
+           !mono_security_core_clr_ensure_reflection_access_field (cf, &error)) {
+               mono_error_set_pending_exception (&error);
+               return NULL;
+       }
 
        MonoObject * result = mono_field_get_value_object_checked (domain, cf, obj, &error);
        mono_error_set_pending_exception (&error);
@@ -1865,8 +1960,11 @@ ves_icall_MonoField_SetValueInternal (MonoReflectionField *field, MonoObject *ob
                return;
        }
 
-       if (mono_security_core_clr_enabled ())
-               mono_security_core_clr_ensure_reflection_access_field (cf);
+       if (mono_security_core_clr_enabled () &&
+           !mono_security_core_clr_ensure_reflection_access_field (cf, &error)) {
+               mono_error_set_pending_exception (&error);
+               return;
+       }
 
        type = mono_field_get_type_checked (cf, &error);
        if (!mono_error_ok (&error)) {
@@ -2111,13 +2209,15 @@ ves_icall_MonoPropertyInfo_get_property_info (const MonoReflectionProperty *prop
 
        if ((req_info & PInfo_ReflectedType) != 0) {
                rt = mono_type_get_object_checked (domain, &property->klass->byval_arg, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
 
                MONO_STRUCT_SETREF (info, parent, rt);
        }
        if ((req_info & PInfo_DeclaringType) != 0) {
                rt = mono_type_get_object_checked (domain, &pproperty->parent->byval_arg, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
 
                MONO_STRUCT_SETREF (info, declaring_type, rt);
        }
@@ -2133,7 +2233,8 @@ ves_icall_MonoPropertyInfo_get_property_info (const MonoReflectionProperty *prop
                    (((pproperty->get->flags & METHOD_ATTRIBUTE_MEMBER_ACCESS_MASK) != METHOD_ATTRIBUTE_PRIVATE) ||
                     pproperty->get->klass == property->klass)) {
                        rm = mono_method_get_object_checked (domain, pproperty->get, property->klass, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return;
                } else {
                        rm = NULL;
                }
@@ -2145,7 +2246,8 @@ ves_icall_MonoPropertyInfo_get_property_info (const MonoReflectionProperty *prop
                    (((pproperty->set->flags & METHOD_ATTRIBUTE_MEMBER_ACCESS_MASK) != METHOD_ATTRIBUTE_PRIVATE) ||
                     pproperty->set->klass == property->klass)) {
                        rm =  mono_method_get_object_checked (domain, pproperty->set, property->klass, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return;
                } else {
                        rm = NULL;
                }
@@ -2167,12 +2269,14 @@ ves_icall_MonoEventInfo_get_event_info (MonoReflectionMonoEvent *event, MonoEven
        MonoDomain *domain = mono_object_domain (event); 
 
        rt = mono_type_get_object_checked (domain, &event->klass->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        MONO_STRUCT_SETREF (info, reflected_type, rt);
 
        rt = mono_type_get_object_checked (domain, &event->event->parent->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        MONO_STRUCT_SETREF (info, declaring_type, rt);
 
@@ -2181,7 +2285,8 @@ ves_icall_MonoEventInfo_get_event_info (MonoReflectionMonoEvent *event, MonoEven
 
        if (event->event->add) {
                rm = mono_method_get_object_checked (domain, event->event->add, NULL, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
        } else {
                rm = NULL;
        }
@@ -2190,7 +2295,8 @@ ves_icall_MonoEventInfo_get_event_info (MonoReflectionMonoEvent *event, MonoEven
 
        if (event->event->remove) {
                rm = mono_method_get_object_checked (domain, event->event->remove, NULL, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
        } else {
                rm = NULL;
        }
@@ -2199,7 +2305,8 @@ ves_icall_MonoEventInfo_get_event_info (MonoReflectionMonoEvent *event, MonoEven
 
        if (event->event->raise) {
                rm = mono_method_get_object_checked (domain, event->event->raise, NULL, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
        } else {
                rm = NULL;
        }
@@ -2211,11 +2318,15 @@ ves_icall_MonoEventInfo_get_event_info (MonoReflectionMonoEvent *event, MonoEven
                int i, n = 0;
                while (event->event->other [n])
                        n++;
-               MONO_STRUCT_SETREF (info, other_methods, mono_array_new (domain, mono_defaults.method_info_class, n));
+               MonoArray *info_arr = mono_array_new_checked (domain, mono_defaults.method_info_class, n, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
+               MONO_STRUCT_SETREF (info, other_methods, info_arr);
 
                for (i = 0; i < n; i++) {
                        rm = mono_method_get_object_checked (domain, event->event->other [i], NULL, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return;
                        mono_array_setref (info->other_methods, i, rm);
                }
        }               
@@ -2316,12 +2427,17 @@ ves_icall_Type_GetInterfaces (MonoReflectionType* type)
        len = g_hash_table_size (iface_hash);
        if (len == 0) {
                g_hash_table_destroy (iface_hash);
-               if (!data.domain->empty_types)
-                       data.domain->empty_types = mono_array_new_cached (data.domain, mono_defaults.monotype_class, 0);
+               if (!data.domain->empty_types) {
+                       data.domain->empty_types = mono_array_new_cached (data.domain, mono_defaults.monotype_class, 0, &error);
+                       if (!is_ok (&error))
+                               goto fail;
+               }
                return data.domain->empty_types;
        }
 
-       data.iface_array = mono_array_new_cached (data.domain, mono_defaults.monotype_class, len);
+       data.iface_array = mono_array_new_cached (data.domain, mono_defaults.monotype_class, len, &error);
+       if (!is_ok (&error))
+               goto fail;
        g_hash_table_foreach (iface_hash, fill_iface_array, &data);
        if (!mono_error_ok (&error))
                goto fail;
@@ -2349,9 +2465,11 @@ ves_icall_Type_GetInterfaceMapData (MonoReflectionType *type, MonoReflectionType
        MonoError error;
 
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
        mono_class_init_checked (iclass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        mono_class_setup_vtable (klass);
 
@@ -2361,15 +2479,23 @@ ves_icall_Type_GetInterfaceMapData (MonoReflectionType *type, MonoReflectionType
 
        len = mono_class_num_methods (iclass);
        domain = mono_object_domain (type);
-       mono_gc_wbarrier_generic_store (targets, (MonoObject*) mono_array_new (domain, mono_defaults.method_info_class, len));
-       mono_gc_wbarrier_generic_store (methods, (MonoObject*) mono_array_new (domain, mono_defaults.method_info_class, len));
+       MonoArray *targets_arr = mono_array_new_checked (domain, mono_defaults.method_info_class, len, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       mono_gc_wbarrier_generic_store (targets, (MonoObject*) targets_arr);
+       MonoArray *methods_arr = mono_array_new_checked (domain, mono_defaults.method_info_class, len, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       mono_gc_wbarrier_generic_store (methods, (MonoObject*) methods_arr);
        iter = NULL;
        while ((method = mono_class_get_methods (iclass, &iter))) {
                member = mono_method_get_object_checked (domain, method, iclass, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
                mono_array_setref (*methods, i, member);
                member = mono_method_get_object_checked (domain, klass->vtable [i + ioffset], klass, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
                mono_array_setref (*targets, i, member);
                
                i ++;
@@ -2383,7 +2509,8 @@ ves_icall_Type_GetPacking (MonoReflectionType *type, guint32 *packing, guint32 *
        MonoClass *klass = mono_class_from_mono_type (type->type);
 
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        if (image_is_dynamic (klass->image)) {
                MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder*)type;
@@ -2403,14 +2530,15 @@ ves_icall_RuntimeTypeHandle_GetElementType (MonoReflectionType *type)
 
        if (!type->type->byref && type->type->type == MONO_TYPE_SZARRAY) {
                ret = mono_type_get_object_checked (mono_object_domain (type), &type->type->data.klass->byval_arg, &error);
-               mono_error_raise_exception (&error);
-
+               mono_error_set_pending_exception (&error);
                return ret;
        }
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
 
        // GetElementType should only return a type for:
        // Array Pointer PassedByRef
@@ -2423,7 +2551,7 @@ ves_icall_RuntimeTypeHandle_GetElementType (MonoReflectionType *type)
        else
                return NULL;
 
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -2442,7 +2570,7 @@ ves_icall_RuntimeTypeHandle_GetBaseType (MonoReflectionType *type)
                return NULL;
 
        ret = mono_type_get_object_checked (mono_object_domain (type), &klass->parent->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -2471,7 +2599,8 @@ ves_icall_RuntimeTypeHandle_IsComObject (MonoReflectionType *type)
        MonoError error;
        MonoClass *klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
 
        return mono_class_is_com_object (klass);
 }
@@ -2492,8 +2621,7 @@ ves_icall_RuntimeTypeHandle_GetModule (MonoReflectionType *type)
        MonoReflectionModule *result = NULL;
        MonoClass *klass = mono_class_from_mono_type (type->type);
        result = mono_module_get_object_checked (mono_object_domain (type), klass->image, &error);
-       if (!mono_error_ok (&error))
-               mono_error_set_pending_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -2504,8 +2632,7 @@ ves_icall_RuntimeTypeHandle_GetAssembly (MonoReflectionType *type)
        MonoDomain *domain = mono_domain_get (); 
        MonoClass *klass = mono_class_from_mono_type (type->type);
        MonoReflectionAssembly *result = mono_assembly_get_object_checked (domain, klass->image->assembly, &error);
-       if (!result)
-               mono_error_set_pending_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -2533,7 +2660,7 @@ ves_icall_MonoType_get_DeclaringType (MonoReflectionType *type)
                return NULL;
 
        ret = mono_type_get_object_checked (domain, &klass->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -2587,11 +2714,9 @@ ves_icall_RuntimeTypeHandle_GetArrayRank (MonoReflectionType *type)
 }
 
 static MonoArray*
-create_type_array (MonoDomain *domain, MonoBoolean runtimeTypeArray, int count)
+create_type_array (MonoDomain *domain, MonoBoolean runtimeTypeArray, int count, MonoError *error)
 {
-       MonoArray *res;
-       res = mono_array_new (domain, runtimeTypeArray ? mono_defaults.runtimetype_class : mono_defaults.systemtype_class, count);
-       return res;
+       return mono_array_new_checked (domain, runtimeTypeArray ? mono_defaults.runtimetype_class : mono_defaults.systemtype_class, count, error);
 }
 
 ICALL_EXPORT MonoArray*
@@ -2608,21 +2733,27 @@ ves_icall_MonoType_GetGenericArguments (MonoReflectionType *type, MonoBoolean ru
 
        if (klass->generic_container) {
                MonoGenericContainer *container = klass->generic_container;
-               res = create_type_array (domain, runtimeTypeArray, container->type_argc);
+               res = create_type_array (domain, runtimeTypeArray, container->type_argc, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
                for (i = 0; i < container->type_argc; ++i) {
                        pklass = mono_class_from_generic_parameter_internal (mono_generic_container_get_param (container, i));
 
                        rt = mono_type_get_object_checked (domain, &pklass->byval_arg, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
 
                        mono_array_setref (res, i, rt);
                }
        } else if (klass->generic_class) {
                MonoGenericInst *inst = klass->generic_class->context.class_inst;
-               res = create_type_array (domain, runtimeTypeArray, inst->type_argc);
+               res = create_type_array (domain, runtimeTypeArray, inst->type_argc, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
                for (i = 0; i < inst->type_argc; ++i) {
                        rt = mono_type_get_object_checked (domain, inst->type_argv [i], &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
 
                        mono_array_setref (res, i, rt);
                }
@@ -2672,7 +2803,7 @@ ves_icall_RuntimeTypeHandle_GetGenericTypeDefinition_impl (MonoReflectionType *t
                        return (MonoReflectionType *)tb;
                else {
                        ret = mono_type_get_object_checked (mono_object_domain (type), &generic_class->byval_arg, &error);
-                       mono_error_raise_exception (&error);
+                       mono_error_set_pending_exception (&error);
 
                        return ret;
                }
@@ -2691,7 +2822,8 @@ ves_icall_Type_MakeGenericType (MonoReflectionType *type, MonoArray *type_array)
 
        g_assert (IS_MONOTYPE (type));
        mono_class_init_checked (mono_class_from_mono_type (type->type), &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        count = mono_array_length (type_array);
        types = g_new0 (MonoType *, count);
@@ -2701,10 +2833,12 @@ ves_icall_Type_MakeGenericType (MonoReflectionType *type, MonoArray *type_array)
                types [i] = t->type;
        }
 
-       geninst = mono_reflection_bind_generic_parameters (type, count, types);
+       geninst = mono_reflection_bind_generic_parameters (type, count, types, &error);
        g_free (types);
-       if (!geninst)
+       if (!geninst) {
+               mono_error_set_pending_exception (&error);
                return NULL;
+       }
 
        klass = mono_class_from_mono_type (geninst);
 
@@ -2715,7 +2849,7 @@ ves_icall_Type_MakeGenericType (MonoReflectionType *type, MonoArray *type_array)
        }
 
        ret = mono_type_get_object_checked (mono_object_domain (type), geninst, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -2772,10 +2906,13 @@ ves_icall_Type_GetGenericParameterConstraints (MonoReflectionType *type)
        for (count = 0, ptr = param_info->constraints; ptr && *ptr; ptr++, count++)
                ;
 
-       res = mono_array_new (domain, mono_defaults.monotype_class, count);
+       res = mono_array_new_checked (domain, mono_defaults.monotype_class, count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        for (i = 0; i < count; i++) {
                rt = mono_type_get_object_checked (domain, &param_info->constraints [i]->byval_arg, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                mono_array_setref (res, i, rt);
        }
@@ -2818,13 +2955,15 @@ ves_icall_MonoType_GetCorrespondingInflatedMethod (MonoReflectionType *type,
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        iter = NULL;
        while ((method = mono_class_get_methods (klass, &iter))) {
                 if (method->token == generic->method->token) {
                        ret = mono_method_get_object_checked (domain, method, klass, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
                }
         }
 
@@ -2994,11 +3133,14 @@ ves_icall_MonoMethod_GetGenericArguments (MonoReflectionMethod *method)
 
                if (inst) {
                        count = inst->type_argc;
-                       res = mono_array_new (domain, mono_defaults.systemtype_class, count);
+                       res = mono_array_new_checked (domain, mono_defaults.systemtype_class, count, &error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
 
                        for (i = 0; i < count; i++) {
                                rt = mono_type_get_object_checked (domain, inst->type_argv [i], &error);
-                               mono_error_raise_exception (&error);
+                               if (mono_error_set_pending_exception (&error))
+                                       return NULL;
 
                                mono_array_setref (res, i, rt);
                        }
@@ -3008,7 +3150,9 @@ ves_icall_MonoMethod_GetGenericArguments (MonoReflectionMethod *method)
        }
 
        count = mono_method_signature (method->method)->generic_param_count;
-       res = mono_array_new (domain, mono_defaults.systemtype_class, count);
+       res = mono_array_new_checked (domain, mono_defaults.systemtype_class, count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        for (i = 0; i < count; i++) {
                MonoGenericContainer *container = mono_method_get_generic_container (method->method);
@@ -3016,7 +3160,8 @@ ves_icall_MonoMethod_GetGenericArguments (MonoReflectionMethod *method)
                MonoClass *pklass = mono_class_from_generic_parameter_internal (param);
 
                rt = mono_type_get_object_checked (domain, &pklass->byval_arg, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                mono_array_setref (res, i, rt);
        }
@@ -3041,8 +3186,11 @@ ves_icall_InternalInvoke (MonoReflectionMethod *method, MonoObject *this_arg, Mo
 
        *exc = NULL;
 
-       if (mono_security_core_clr_enabled ())
-               mono_security_core_clr_ensure_reflection_access_method (m);
+       if (mono_security_core_clr_enabled () &&
+           !mono_security_core_clr_ensure_reflection_access_method (m, &error)) {
+               mono_error_set_pending_exception (&error);
+               return NULL;
+       }
 
        if (!(m->flags & METHOD_ATTRIBUTE_STATIC)) {
                if (!mono_class_vtable_full (mono_object_domain (method), m->klass, &error)) {
@@ -3052,7 +3200,11 @@ ves_icall_InternalInvoke (MonoReflectionMethod *method, MonoObject *this_arg, Mo
                }
 
                if (this_arg) {
-                       if (!mono_object_isinst (this_arg, m->klass)) {
+                       if (!mono_object_isinst_checked (this_arg, m->klass, &error)) {
+                               if (!is_ok (&error)) {
+                                       mono_gc_wbarrier_generic_store (exc, (MonoObject*) mono_error_convert_to_exception (&error));
+                                       return NULL;
+                               }
                                char *this_name = mono_type_get_full_name (mono_object_get_class (this_arg));
                                char *target_name = mono_type_get_full_name (m->klass);
                                char *msg = g_strdup_printf ("Object of type '%s' doesn't match target type '%s'", this_name, target_name);
@@ -3164,6 +3316,7 @@ ves_icall_InternalInvoke (MonoReflectionMethod *method, MonoObject *this_arg, Mo
 ICALL_EXPORT MonoObject *
 ves_icall_InternalExecute (MonoReflectionMethod *method, MonoObject *this_arg, MonoArray *params, MonoArray **outArgs) 
 {
+       MonoError error;
        MonoDomain *domain = mono_object_domain (method); 
        MonoMethod *m = method->method;
        MonoMethodSignature *sig = mono_method_signature (m);
@@ -3191,16 +3344,20 @@ ves_icall_InternalExecute (MonoReflectionMethod *method, MonoObject *this_arg, M
                        do {
                                MonoClassField* field = mono_class_get_field_from_name (k, str);
                                if (field) {
+                                       g_free (str);
                                        MonoClass *field_klass =  mono_class_from_mono_type (field->type);
-                                       if (field_klass->valuetype)
-                                               result = mono_value_box (domain, field_klass, (char *)this_arg + field->offset);
-                                       else 
+                                       if (field_klass->valuetype) {
+                                               result = mono_value_box_checked (domain, field_klass, (char *)this_arg + field->offset, &error);
+                                               if (mono_error_set_pending_exception (&error))
+                                                       return NULL;
+                                       } else 
                                                result = (MonoObject *)*((gpointer *)((char *)this_arg + field->offset));
                                
-                                       out_args = mono_array_new (domain, mono_defaults.object_class, 1);
+                                       out_args = mono_array_new_checked (domain, mono_defaults.object_class, 1, &error);
+                                       if (mono_error_set_pending_exception (&error))
+                                               return NULL;
                                        mono_gc_wbarrier_generic_store (outArgs, (MonoObject*) out_args);
                                        mono_array_setref (out_args, 0, result);
-                                       g_free (str);
                                        return NULL;
                                }
                                k = k->parent;
@@ -3230,6 +3387,7 @@ ves_icall_InternalExecute (MonoReflectionMethod *method, MonoObject *this_arg, M
                        do {
                                MonoClassField* field = mono_class_get_field_from_name (k, str);
                                if (field) {
+                                       g_free (str);
                                        MonoClass *field_klass =  mono_class_from_mono_type (field->type);
                                        MonoObject *val = (MonoObject *)mono_array_get (params, gpointer, 2);
 
@@ -3241,10 +3399,11 @@ ves_icall_InternalExecute (MonoReflectionMethod *method, MonoObject *this_arg, M
                                                mono_gc_wbarrier_set_field (this_arg, (char*)this_arg + field->offset, val);
                                        }
                                
-                                       out_args = mono_array_new (domain, mono_defaults.object_class, 0);
+                                       out_args = mono_array_new_checked (domain, mono_defaults.object_class, 0, &error);
+                                       if (mono_error_set_pending_exception (&error))
+                                               return NULL;
                                        mono_gc_wbarrier_generic_store (outArgs, (MonoObject*) out_args);
 
-                                       g_free (str);
                                        return NULL;
                                }
                                
@@ -3262,8 +3421,10 @@ ves_icall_InternalExecute (MonoReflectionMethod *method, MonoObject *this_arg, M
                        outarg_count++;
        }
 
-       out_args = mono_array_new (domain, mono_defaults.object_class, outarg_count);
-       
+       out_args = mono_array_new_checked (domain, mono_defaults.object_class, outarg_count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
        /* handle constructors only for objects already allocated */
        if (!strcmp (method->method->name, ".ctor"))
                g_assert (this_arg);
@@ -3325,7 +3486,8 @@ write_enum_value (char *mem, int type, guint64 value)
                break;
        }
        case MONO_TYPE_U2:
-       case MONO_TYPE_I2: {
+       case MONO_TYPE_I2:
+       case MONO_TYPE_CHAR: {
                guint16 *p = (guint16 *)mem;
                *p = value;
                break;
@@ -3361,12 +3523,14 @@ ves_icall_System_Enum_ToObject (MonoReflectionType *enumType, guint64 value)
        enumc = mono_class_from_mono_type (enumType->type);
 
        mono_class_init_checked (enumc, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        etype = mono_class_enum_basetype (enumc);
 
        res = mono_object_new_checked (domain, enumc, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        write_enum_value ((char *)res + sizeof (MonoObject), etype->type, value);
 
        return res;
@@ -3401,7 +3565,8 @@ ves_icall_System_Enum_get_value (MonoObject *eobj)
        
        enumc = mono_class_from_mono_type (mono_class_enum_basetype (eobj->vtable->klass));
        res = mono_object_new_checked (mono_object_domain (eobj), enumc, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        dst = (char *)res + sizeof (MonoObject);
        src = (char *)eobj + sizeof (MonoObject);
        size = mono_class_value_size (enumc, NULL);
@@ -3421,7 +3586,8 @@ ves_icall_System_Enum_get_underlying_type (MonoReflectionType *type)
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        etype = mono_class_enum_basetype (klass);
        if (!etype) {
@@ -3430,7 +3596,7 @@ ves_icall_System_Enum_get_underlying_type (MonoReflectionType *type)
        }
 
        ret = mono_type_get_object_checked (mono_object_domain (type), etype, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -3534,7 +3700,9 @@ ves_icall_System_Enum_GetEnumValuesAndNames (MonoReflectionType *type, MonoArray
        gboolean sorted = TRUE;
 
        mono_class_init_checked (enumc, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
+
 
        if (!enumc->enumtype) {
                mono_set_pending_exception (mono_get_exception_argument ("enumType", "Type provided must be an Enum."));
@@ -3544,8 +3712,12 @@ ves_icall_System_Enum_GetEnumValuesAndNames (MonoReflectionType *type, MonoArray
        base_type = mono_class_enum_basetype (enumc)->type;
 
        nvalues = mono_class_num_fields (enumc) ? mono_class_num_fields (enumc) - 1 : 0;
-       *names = mono_array_new (domain, mono_defaults.string_class, nvalues);
-       *values = mono_array_new (domain, mono_defaults.uint64_class, nvalues);
+       *names = mono_array_new_checked (domain, mono_defaults.string_class, nvalues, &error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
+       *values = mono_array_new_checked (domain, mono_defaults.uint64_class, nvalues, &error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
 
        iter = NULL;
        while ((field = mono_class_get_fields (enumc, &iter))) {
@@ -3611,8 +3783,11 @@ ves_icall_Type_GetFields_internal (MonoReflectionType *type, MonoString *name, g
        MonoPtrArray tmp_array;
 
        domain = ((MonoObject *)type)->vtable->domain;
-       if (type->type->byref)
-               return mono_array_new (domain, mono_defaults.field_info_class, 0);
+       if (type->type->byref) {
+               MonoArray *result = mono_array_new_checked (domain, mono_defaults.field_info_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return result;
+       }
 
        klass = startklass = mono_class_from_mono_type (type->type);
        refklass = mono_class_from_mono_type (reftype->type);
@@ -3673,7 +3848,9 @@ handle_parent:
        if (!(bflags & BFLAGS_DeclaredOnly) && (klass = klass->parent))
                goto handle_parent;
 
-       res = mono_array_new_cached (domain, mono_defaults.field_info_class, mono_ptr_array_size (tmp_array));
+       res = mono_array_new_cached (domain, mono_defaults.field_info_class, mono_ptr_array_size (tmp_array), &error);
+       if (!is_ok (&error))
+               goto fail;
 
        for (i = 0; i < mono_ptr_array_size (tmp_array); ++i)
                mono_array_setref (res, i, mono_ptr_array_get (tmp_array, i));
@@ -3686,8 +3863,8 @@ handle_parent:
        return res;
 fail:
        mono_ptr_array_destroy (tmp_array);
-       mono_error_raise_exception (&error);
-       g_assert_not_reached ();
+       mono_error_set_pending_exception (&error);
+       return NULL;
 }
 
 static gboolean
@@ -3728,8 +3905,7 @@ mono_class_get_methods_by_name (MonoClass *klass, const char *name, guint32 bfla
        /* An optimization for calls made from Delegate:CreateDelegate () */
        if (klass->delegate && name && !strcmp (name, "Invoke") && (bflags == (BFLAGS_Public | BFLAGS_Static | BFLAGS_Instance))) {
                method = mono_get_delegate_invoke (klass);
-               if (mono_loader_get_last_error ())
-                       goto loader_error;
+               g_assert (method);
 
                g_ptr_array_add (array, method);
                return array;
@@ -3737,7 +3913,7 @@ mono_class_get_methods_by_name (MonoClass *klass, const char *name, guint32 bfla
 
        mono_class_setup_methods (klass);
        mono_class_setup_vtable (klass);
-       if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+       if (mono_class_has_failure (klass))
                goto loader_error;
 
        if (is_generic_parameter (&klass->byval_arg))
@@ -3753,7 +3929,7 @@ mono_class_get_methods_by_name (MonoClass *klass, const char *name, guint32 bfla
 handle_parent:
        mono_class_setup_methods (klass);
        mono_class_setup_vtable (klass);
-       if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+       if (mono_class_has_failure (klass))
                goto loader_error;              
 
        iter = NULL;
@@ -3813,8 +3989,7 @@ loader_error:
        if (mono_class_has_failure (klass)) {
                *ex = mono_class_get_exception_for_failure (klass);
        } else {
-               *ex = mono_loader_error_prepare_exception (mono_loader_get_last_error ());
-               mono_loader_clear_error ();
+               *ex = mono_get_exception_execution_engine ("Unknown error");
        }
        return NULL;
 }
@@ -3892,7 +4067,7 @@ ves_icall_Type_GetConstructors_internal (MonoReflectionType *type, guint32 bflag
 {
        MonoDomain *domain; 
        MonoClass *startklass, *klass, *refklass;
-       MonoArray *res;
+       MonoArray *res = NULL;
        MonoMethod *method;
        MonoObject *member;
        int i, match;
@@ -3900,18 +4075,23 @@ ves_icall_Type_GetConstructors_internal (MonoReflectionType *type, guint32 bflag
        MonoPtrArray tmp_array;
        MonoError error;
        
+       domain = ((MonoObject *)type)->vtable->domain;
+       if (type->type->byref) {
+               res = mono_array_new_cached (domain, mono_defaults.method_info_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
+       }
+
        mono_ptr_array_init (tmp_array, 4, MONO_ROOT_SOURCE_REFLECTION, "temporary reflection constructors list"); /*FIXME, guestimating*/
 
-       domain = ((MonoObject *)type)->vtable->domain;
-       if (type->type->byref)
-               return mono_array_new_cached (domain, mono_defaults.method_info_class, 0);
+
        klass = startklass = mono_class_from_mono_type (type->type);
        refklass = mono_class_from_mono_type (reftype->type);
 
        mono_class_setup_methods (klass);
        if (mono_class_has_failure (klass)) {
                mono_set_pending_exception (mono_class_get_exception_for_failure (klass));
-               return NULL;
+               goto leave;
        }
 
        iter = NULL;
@@ -3941,19 +4121,20 @@ ves_icall_Type_GetConstructors_internal (MonoReflectionType *type, guint32 bflag
                if (!match)
                        continue;
                member = (MonoObject*)mono_method_get_object_checked (domain, method, refklass, &error);
-               if (!mono_error_ok (&error)) {
-                       mono_error_set_pending_exception (&error);
-                       return NULL;
-               }
+               if (mono_error_set_pending_exception (&error))
+                       goto leave;
 
                mono_ptr_array_append (tmp_array, member);
        }
 
-       res = mono_array_new_cached (domain, mono_class_get_constructor_info_class (), mono_ptr_array_size (tmp_array));
+       res = mono_array_new_cached (domain, mono_class_get_constructor_info_class (), mono_ptr_array_size (tmp_array), &error);
+       if (mono_error_set_pending_exception (&error))
+               goto leave;
 
        for (i = 0; i < mono_ptr_array_size (tmp_array); ++i)
                mono_array_setref (res, i, mono_ptr_array_get (tmp_array, i));
 
+leave:
        mono_ptr_array_destroy (tmp_array);
 
        return res;
@@ -4036,11 +4217,15 @@ ves_icall_Type_GetPropertiesByName (MonoReflectionType *type, MonoString *name,
 
        mono_error_init (&error);
        
+       domain = ((MonoObject *)type)->vtable->domain;
+       if (type->type->byref) {
+               res = mono_array_new_cached (domain, mono_class_get_property_info_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
+       }
+
        mono_ptr_array_init (tmp_array, 8, MONO_ROOT_SOURCE_REFLECTION, "temporary reflection properties list"); /*This the average for ASP.NET types*/
 
-       domain = ((MonoObject *)type)->vtable->domain;
-       if (type->type->byref)
-               return mono_array_new_cached (domain, mono_class_get_property_info_class (), 0);
        klass = startklass = mono_class_from_mono_type (type->type);
 
        if (name != NULL) {
@@ -4052,7 +4237,7 @@ ves_icall_Type_GetPropertiesByName (MonoReflectionType *type, MonoString *name,
 handle_parent:
        mono_class_setup_methods (klass);
        mono_class_setup_vtable (klass);
-       if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+       if (mono_class_has_failure (klass))
                goto loader_error;
 
        iter = NULL;
@@ -4112,7 +4297,9 @@ handle_parent:
        g_hash_table_destroy (properties);
        g_free (propname);
 
-       res = mono_array_new_cached (domain, mono_class_get_property_info_class (), mono_ptr_array_size (tmp_array));
+       res = mono_array_new_cached (domain, mono_class_get_property_info_class (), mono_ptr_array_size (tmp_array), &error);
+       if (!is_ok (&error))
+               goto failure;
        for (i = 0; i < mono_ptr_array_size (tmp_array); ++i)
                mono_array_setref (res, i, mono_ptr_array_get (tmp_array, i));
 
@@ -4125,9 +4312,6 @@ handle_parent:
 loader_error:
        if (mono_class_has_failure (klass)) {
                mono_error_set_exception_instance (&error, mono_class_get_exception_for_failure (klass));
-       } else {
-               mono_error_set_from_loader_error (&error);
-               mono_loader_clear_error ();
        }
 
 failure:
@@ -4175,18 +4359,22 @@ ves_icall_Type_GetEvents_internal (MonoReflectionType *type, MonoString *name, g
 
        mono_error_init (&error);
        
+       domain = mono_object_domain (type);
+       if (type->type->byref) {
+               res = mono_array_new_cached (domain, mono_class_get_event_info_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
+       }
+
        mono_ptr_array_init (tmp_array, 4, MONO_ROOT_SOURCE_REFLECTION, "temporary reflection events list");
 
-       domain = mono_object_domain (type);
-       if (type->type->byref)
-               return mono_array_new_cached (domain, mono_class_get_event_info_class (), 0);
        klass = startklass = mono_class_from_mono_type (type->type);
 
        events = g_hash_table_new (event_hash, (GEqualFunc)event_equal);
 handle_parent:
        mono_class_setup_methods (klass);
        mono_class_setup_vtable (klass);
-       if (mono_class_has_failure (klass) || mono_loader_get_last_error ())
+       if (mono_class_has_failure (klass))
                goto loader_error;
 
        iter = NULL;
@@ -4254,7 +4442,9 @@ handle_parent:
 
        g_hash_table_destroy (events);
 
-       res = mono_array_new_cached (domain, mono_class_get_event_info_class (), mono_ptr_array_size (tmp_array));
+       res = mono_array_new_cached (domain, mono_class_get_event_info_class (), mono_ptr_array_size (tmp_array), &error);
+       if (!is_ok (&error))
+               goto failure;
 
        for (i = 0; i < mono_ptr_array_size (tmp_array); ++i)
                mono_array_setref (res, i, mono_ptr_array_get (tmp_array, i));
@@ -4269,9 +4459,6 @@ handle_parent:
 loader_error:
        if (mono_class_has_failure (klass)) {
                mono_error_set_exception_instance (&error, mono_class_get_exception_for_failure (klass));
-       } else {
-               mono_error_set_from_loader_error (&error);
-               mono_loader_clear_error ();
        }
 
 failure:
@@ -4294,16 +4481,21 @@ ves_icall_Type_GetNestedTypes (MonoReflectionType *type, MonoString *name, guint
        MonoReflectionType *rt;
        MonoDomain *domain; 
        MonoClass *klass;
-       MonoArray *res;
+       MonoArray *res = NULL;
        int i, match;
        MonoClass *nested;
        gpointer iter;
        char *str = NULL;
        MonoPtrArray tmp_array;
 
+       mono_error_init (&error);
+
        domain = ((MonoObject *)type)->vtable->domain;
-       if (type->type->byref)
-               return mono_array_new (domain, mono_defaults.monotype_class, 0);
+       if (type->type->byref) {
+               MonoArray *result = mono_array_new_cached (domain, mono_defaults.monotype_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return result;
+       }
        klass = mono_class_from_mono_type (type->type);
 
        /*
@@ -4343,21 +4535,25 @@ ves_icall_Type_GetNestedTypes (MonoReflectionType *type, MonoString *name, guint
                }
 
                rt = mono_type_get_object_checked (domain, &nested->byval_arg, &error);
-               mono_error_raise_exception (&error);
+               if (!is_ok (&error))
+                       goto leave;
 
                mono_ptr_array_append (tmp_array, (MonoObject*) rt);
        }
 
-       res = mono_array_new_cached (domain, mono_defaults.monotype_class, mono_ptr_array_size (tmp_array));
+       res = mono_array_new_cached (domain, mono_defaults.monotype_class, mono_ptr_array_size (tmp_array), &error);
+       if (!is_ok (&error))
+               goto leave;
 
        for (i = 0; i < mono_ptr_array_size (tmp_array); ++i)
                mono_array_setref (res, i, mono_ptr_array_get (tmp_array, i));
 
+leave:
        mono_ptr_array_destroy (tmp_array);
 
-       if (!str)
-               g_free (str);
+       g_free (str);
 
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -4402,7 +4598,7 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
 
        if (module != NULL) {
                if (module->image) {
-                       type = mono_reflection_get_type_checked (module->image, &info, ignoreCase, &type_resolve, &error);
+                       type = mono_reflection_get_type_checked (module->image, module->image, &info, ignoreCase, &type_resolve, &error);
                        if (!is_ok (&error)) {
                                g_free (str);
                                mono_reflection_free_type_info (&info);
@@ -4422,7 +4618,7 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
                        if (abuilder->modules) {
                                for (i = 0; i < mono_array_length (abuilder->modules); ++i) {
                                        MonoReflectionModuleBuilder *mb = mono_array_get (abuilder->modules, MonoReflectionModuleBuilder*, i);
-                                       type = mono_reflection_get_type_checked (&mb->dynamic_image->image, &info, ignoreCase, &type_resolve, &error);
+                                       type = mono_reflection_get_type_checked (&mb->dynamic_image->image, &mb->dynamic_image->image, &info, ignoreCase, &type_resolve, &error);
                                        if (!is_ok (&error)) {
                                                g_free (str);
                                                mono_reflection_free_type_info (&info);
@@ -4437,7 +4633,7 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
                        if (!type && abuilder->loaded_modules) {
                                for (i = 0; i < mono_array_length (abuilder->loaded_modules); ++i) {
                                        MonoReflectionModule *mod = mono_array_get (abuilder->loaded_modules, MonoReflectionModule*, i);
-                                       type = mono_reflection_get_type_checked (mod->image, &info, ignoreCase, &type_resolve, &error);
+                                       type = mono_reflection_get_type_checked (mod->image, mod->image, &info, ignoreCase, &type_resolve, &error);
                                        if (!is_ok (&error)) {
                                                g_free (str);
                                                mono_reflection_free_type_info (&info);
@@ -4450,7 +4646,7 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
                        }
                }
                else {
-                       type = mono_reflection_get_type_checked (assembly->assembly->image, &info, ignoreCase, &type_resolve, &error);
+                       type = mono_reflection_get_type_checked (assembly->assembly->image, assembly->assembly->image, &info, ignoreCase, &type_resolve, &error);
                        if (!is_ok (&error)) {
                                g_free (str);
                                mono_reflection_free_type_info (&info);
@@ -4466,20 +4662,9 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
                if (throwOnError)
                        e = mono_get_exception_type_load (name, NULL);
 
-               if (mono_loader_get_last_error () && mono_defaults.generic_ilist_class)
-                       e = mono_loader_error_prepare_exception (mono_loader_get_last_error ());
-
-               mono_loader_clear_error ();
-
                if (e != NULL)
                        mono_set_pending_exception (e);
                return NULL;
-       } else if (mono_loader_get_last_error ()) {
-               if (throwOnError) {
-                       mono_set_pending_exception (mono_loader_error_prepare_exception (mono_loader_get_last_error ()));
-                       return NULL;
-               }
-               mono_loader_clear_error ();
        }
 
        if (type->type == MONO_TYPE_CLASS) {
@@ -4489,7 +4674,6 @@ ves_icall_System_Reflection_Assembly_InternalGetType (MonoReflectionAssembly *as
                if (throwOnError && mono_class_has_failure (klass)) {
                        /* report SecurityException (or others) that occured when loading the assembly */
                        MonoException *exc = mono_class_get_exception_for_failure (klass);
-                       mono_loader_clear_error ();
                        mono_set_pending_exception (exc);
                        return NULL;
                }
@@ -4673,8 +4857,11 @@ ves_icall_System_Reflection_Assembly_GetManifestModuleInternal (MonoReflectionAs
 ICALL_EXPORT MonoArray*
 ves_icall_System_Reflection_Assembly_GetManifestResourceNames (MonoReflectionAssembly *assembly) 
 {
+       MonoError error;
        MonoTableInfo *table = &assembly->assembly->image->tables [MONO_TABLE_MANIFESTRESOURCE];
-       MonoArray *result = mono_array_new (mono_object_domain (assembly), mono_defaults.string_class, table->rows);
+       MonoArray *result = mono_array_new_checked (mono_object_domain (assembly), mono_defaults.string_class, table->rows, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        int i;
        const char *val;
 
@@ -4730,7 +4917,10 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
        t = &assembly->assembly->image->tables [MONO_TABLE_ASSEMBLYREF];
        count = t->rows;
 
-       result = mono_array_new (domain, mono_class_get_assembly_name_class (), count);
+       result = mono_array_new_checked (domain, mono_class_get_assembly_name_class (), count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
 
        if (count > 0 && !create_culture) {
                MonoMethodDesc *desc = mono_method_desc_new (
@@ -4749,7 +4939,8 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
 
                aname = (MonoReflectionAssemblyName *) mono_object_new_checked (
                        domain, mono_class_get_assembly_name_class (), &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                MONO_OBJECT_SETREF (aname, name, mono_string_new (domain, mono_metadata_string_heap (image, cols [MONO_ASSEMBLYREF_NAME])));
 
@@ -4762,7 +4953,8 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                aname->hashalg = ASSEMBLY_HASH_SHA1; /* SHA1 (default) */
 
                version = create_version (domain, aname->major, aname->minor, aname->build, aname->revision, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                MONO_OBJECT_SETREF (aname, version, version);
 
@@ -4773,7 +4965,8 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                        args [1] = &assembly_ref;
 
                        o = mono_runtime_invoke_checked (create_culture, NULL, args, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
 
                        MONO_OBJECT_SETREF (aname, cultureInfo, o);
                }
@@ -4785,14 +4978,26 @@ ves_icall_System_Reflection_Assembly_GetReferencedAssemblies (MonoReflectionAsse
                        if ((cols [MONO_ASSEMBLYREF_FLAGS] & ASSEMBLYREF_FULL_PUBLIC_KEY_FLAG)) {
                                /* public key token isn't copied - the class library will 
                                automatically generate it from the public key if required */
-                               MONO_OBJECT_SETREF (aname, publicKey, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
-                               memcpy (mono_array_addr (aname->publicKey, guint8, 0), pkey_ptr, pkey_len);
+                               MonoArray *pkey = mono_array_new_checked (domain, mono_defaults.byte_class, pkey_len, &error);
+                               if (mono_error_set_pending_exception (&error))
+                                       return NULL;
+
+                               MONO_OBJECT_SETREF (aname, publicKey, pkey);
+                               memcpy (mono_array_addr (pkey, guint8, 0), pkey_ptr, pkey_len);
                        } else {
-                               MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
-                               memcpy (mono_array_addr (aname->keyToken, guint8, 0), pkey_ptr, pkey_len);
+                               MonoArray *keyToken = mono_array_new_checked (domain, mono_defaults.byte_class, pkey_len, &error);
+                               if (mono_error_set_pending_exception (&error))
+                                       return NULL;
+
+                               MONO_OBJECT_SETREF (aname, keyToken, keyToken);
+                               memcpy (mono_array_addr (keyToken, guint8, 0), pkey_ptr, pkey_len);
                        }
                } else {
-                       MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, 0));
+                       MonoArray *keyToken = mono_array_new_checked (domain, mono_defaults.byte_class, 0, &error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
+
+                       MONO_OBJECT_SETREF (aname, keyToken, keyToken);
                }
                
                /* note: this function doesn't return the codebase on purpose (i.e. it can
@@ -4860,7 +5065,8 @@ ves_icall_System_Reflection_Assembly_GetManifestResourceInternal (MonoReflection
 
        
        MonoReflectionModule *rm = mono_module_get_object_checked (mono_domain_get (), module, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        mono_gc_wbarrier_generic_store (ref_module, (MonoObject*) rm);
 
        return (void*)mono_image_get_resource (module, cols [MONO_MANIFEST_OFFSET], (guint32*)size);
@@ -4940,6 +5146,7 @@ ves_icall_System_Reflection_Assembly_GetManifestResourceInfoInternal (MonoReflec
 ICALL_EXPORT MonoObject*
 ves_icall_System_Reflection_Assembly_GetFilesInternal (MonoReflectionAssembly *assembly, MonoString *name, MonoBoolean resource_modules) 
 {
+       MonoError error;
        MonoTableInfo *table = &assembly->assembly->image->tables [MONO_TABLE_FILE];
        MonoArray *result = NULL;
        int i, count;
@@ -4970,7 +5177,10 @@ ves_icall_System_Reflection_Assembly_GetFilesInternal (MonoReflectionAssembly *a
                        count ++;
        }
 
-       result = mono_array_new (mono_object_domain (assembly), mono_defaults.string_class, count);
+       result = mono_array_new_checked (mono_object_domain (assembly), mono_defaults.string_class, count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
 
        count = 0;
        for (i = 0; i < table->rows; ++i) {
@@ -5014,16 +5224,21 @@ ves_icall_System_Reflection_Assembly_GetModulesInternal (MonoReflectionAssembly
                        real_module_count ++;
 
        klass = mono_class_get_module_class ();
-       res = mono_array_new (domain, klass, 1 + real_module_count + file_count);
+       res = mono_array_new_checked (domain, klass, 1 + real_module_count + file_count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        MonoReflectionModule *image_obj = mono_module_get_object_checked (domain, image, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
        mono_array_setref (res, 0, image_obj);
        j = 1;
        for (i = 0; i < module_count; ++i)
                if (modules [i]) {
                        MonoReflectionModule *rm = mono_module_get_object_checked (domain, modules[i], &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
                        mono_array_setref (res, j, rm);
                        ++j;
                }
@@ -5032,7 +5247,8 @@ ves_icall_System_Reflection_Assembly_GetModulesInternal (MonoReflectionAssembly
                mono_metadata_decode_row (table, i, cols, MONO_FILE_SIZE);
                if (cols [MONO_FILE_FLAGS] && FILE_CONTAINS_NO_METADATA) {
                        MonoReflectionModule *rm = mono_module_file_get_object_checked (domain, image, i, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
                        mono_array_setref (res, j, rm);
                }
                else {
@@ -5043,7 +5259,8 @@ ves_icall_System_Reflection_Assembly_GetModulesInternal (MonoReflectionAssembly
                                return NULL;
                        }
                        MonoReflectionModule *rm = mono_module_get_object_checked (domain, m, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
                        mono_array_setref (res, j, rm);
                }
        }
@@ -5068,7 +5285,7 @@ ves_icall_GetCurrentMethod (void)
                m = ((MonoMethodInflated*)m)->declaring;
 
        res = mono_method_get_object_checked (mono_domain_get (), m, NULL, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -5128,7 +5345,7 @@ ves_icall_System_Reflection_MethodBase_GetMethodFromHandleInternalType (MonoMeth
        } else
                klass = method->klass;
        res = mono_method_get_object_checked (mono_domain_get (), method, klass, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -5235,7 +5452,7 @@ vell_icall_MonoType_get_core_clr_security_level (MonoReflectionType *rfield)
        MonoClass *klass = mono_class_from_mono_type (rfield->type);
 
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return mono_security_core_clr_class_level (klass);
 }
 
@@ -5337,11 +5554,15 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
                pkey_ptr = (char*)name->public_key;
                pkey_len = mono_metadata_decode_blob_size (pkey_ptr, &pkey_ptr);
 
-               MONO_OBJECT_SETREF (aname, publicKey, mono_array_new (domain, mono_defaults.byte_class, pkey_len));
+               MonoArray *pkey = mono_array_new_checked (domain, mono_defaults.byte_class, pkey_len, error);
+               return_if_nok (error);
+               MONO_OBJECT_SETREF (aname, publicKey, pkey);
                memcpy (mono_array_addr (aname->publicKey, guint8, 0), pkey_ptr, pkey_len);
                aname->flags |= ASSEMBLYREF_FULL_PUBLIC_KEY_FLAG;
        } else if (default_publickey) {
-               MONO_OBJECT_SETREF (aname, publicKey, mono_array_new (domain, mono_defaults.byte_class, 0));
+               MonoArray *pkey = mono_array_new_checked (domain, mono_defaults.byte_class, 0, error);
+               return_if_nok (error);
+               MONO_OBJECT_SETREF (aname, publicKey, pkey);
                aname->flags |= ASSEMBLYREF_FULL_PUBLIC_KEY_FLAG;
        }
 
@@ -5350,8 +5571,11 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
                int i, j;
                char *p;
 
-               MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, 8));
-               p = mono_array_addr (aname->keyToken, char, 0);
+               MonoArray *keyToken = mono_array_new_checked (domain, mono_defaults.byte_class, 8, error);
+               return_if_nok (error);
+               
+               MONO_OBJECT_SETREF (aname, keyToken, keyToken);
+               p = mono_array_addr (keyToken, char, 0);
 
                for (i = 0, j = 0; i < 8; i++) {
                        *p = g_ascii_xdigit_value (name->public_key_token [j++]) << 4;
@@ -5359,7 +5583,9 @@ fill_reflection_assembly_name (MonoDomain *domain, MonoReflectionAssemblyName *a
                        p++;
                }
        } else if (default_token) {
-               MONO_OBJECT_SETREF (aname, keyToken, mono_array_new (domain, mono_defaults.byte_class, 0));
+               MonoArray *keyToken = mono_array_new_checked (domain, mono_defaults.byte_class, 0, error);
+               return_if_nok (error);
+               MONO_OBJECT_SETREF (aname, keyToken, keyToken);
        }
 }
 
@@ -5509,14 +5735,14 @@ mono_module_get_types (MonoDomain *domain, MonoImage *image, MonoArray **excepti
        } else {
                count = tdef->rows - 1;
        }
-       res = mono_array_new (domain, mono_defaults.monotype_class, count);
-       *exceptions = mono_array_new (domain, mono_defaults.exception_class, count);
+       res = mono_array_new_checked (domain, mono_defaults.monotype_class, count, error);
+       return_val_if_nok (error, NULL);
+       *exceptions = mono_array_new_checked (domain, mono_defaults.exception_class, count, error);
+       return_val_if_nok (error, NULL);
        count = 0;
        for (i = 1; i < tdef->rows; ++i) {
                if (!exportedOnly || mono_module_type_is_visible (tdef, image, i + 1)) {
                        klass = mono_class_get_checked (image, (i + 1) | MONO_TOKEN_TYPE_DEF, error);
-                       mono_loader_assert_no_error (); /* Plug any leaks */
-                       mono_error_assert_ok (error);
                        
                        if (klass) {
                                rt = mono_type_get_object_checked (domain, &klass->byval_arg, error);
@@ -5552,7 +5778,8 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
        image = assembly->assembly->image;
        table = &image->tables [MONO_TABLE_FILE];
        res = mono_module_get_types (domain, image, &exceptions, exportedOnly, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        /* Append data from all modules in the assembly */
        for (i = 0; i < table->rows; ++i) {
@@ -5563,7 +5790,9 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                                MonoArray *res2;
 
                                res2 = mono_module_get_types (domain, loaded_image, &ex2, exportedOnly, &error);
-                               mono_error_raise_exception (&error);
+                               if (mono_error_set_pending_exception (&error))
+                                       return NULL;
+
 
                                /* Append the new types to the end of the array */
                                if (mono_array_length (res2) > 0) {
@@ -5573,12 +5802,16 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                                        len1 = mono_array_length (res);
                                        len2 = mono_array_length (res2);
 
-                                       res3 = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
+                                       res3 = mono_array_new_checked (domain, mono_defaults.monotype_class, len1 + len2, &error);
+                                       if (mono_error_set_pending_exception (&error))
+                                               return NULL;
                                        mono_array_memcpy_refs (res3, 0, res, 0, len1);
                                        mono_array_memcpy_refs (res3, len1, res2, 0, len2);
                                        res = res3;
 
-                                       ex3 = mono_array_new (domain, mono_defaults.monotype_class, len1 + len2);
+                                       ex3 = mono_array_new_checked (domain, mono_defaults.monotype_class, len1 + len2, &error);
+                                       if (mono_error_set_pending_exception (&error))
+                                               return NULL;
                                        mono_array_memcpy_refs (ex3, 0, exceptions, 0, len1);
                                        mono_array_memcpy_refs (ex3, len1, ex2, 0, len2);
                                        exceptions = ex3;
@@ -5618,9 +5851,11 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                MonoArray *exl = NULL;
                int j, length = g_list_length (list) + ex_count;
 
-               mono_loader_clear_error ();
-
-               exl = mono_array_new (domain, mono_defaults.exception_class, length);
+               exl = mono_array_new_checked (domain, mono_defaults.exception_class, length, &error);
+               if (mono_error_set_pending_exception (&error)) {
+                       g_list_free (list);
+                       return NULL;
+               }
                /* Types for which mono_class_get_checked () succeeded */
                for (i = 0, tmp = list; tmp; i++, tmp = tmp->next) {
                        MonoException *exc = mono_class_get_exception_for_failure ((MonoClass *)tmp->data);
@@ -5643,7 +5878,6 @@ ves_icall_System_Reflection_Assembly_GetTypes (MonoReflectionAssembly *assembly,
                        mono_error_set_pending_exception (&error);
                        return NULL;
                }
-               mono_loader_clear_error ();
                mono_set_pending_exception (exc);
                return NULL;
        }
@@ -5762,13 +5996,16 @@ ves_icall_System_Reflection_Module_InternalGetTypes (MonoReflectionModule *modul
        MonoArray *exceptions;
        int i;
 
-       if (!module->image)
-               return mono_array_new (mono_object_domain (module), mono_defaults.monotype_class, 0);
-       else {
+       if (!module->image) {
+               MonoArray *arr = mono_array_new_checked (mono_object_domain (module), mono_defaults.monotype_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return arr;
+       } else {
                MonoArray *res;
 
                res = mono_module_get_types (mono_object_domain (module), module->image, &exceptions, FALSE, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                for (i = 0; i < mono_array_length (exceptions); ++i) {
                        MonoException *ex = mono_array_get (exceptions, MonoException *, i);
@@ -5792,10 +6029,13 @@ mono_memberref_is_method (MonoImage *image, guint32 token)
                mono_metadata_decode_blob_size (sig, &sig);
                return (*sig != 0x6);
        } else {
+               MonoError error;
                MonoClass *handle_class;
 
-               if (!mono_lookup_dynamic_token_class (image, token, FALSE, &handle_class, NULL))
+               if (!mono_lookup_dynamic_token_class (image, token, FALSE, &handle_class, NULL, &error)) {
+                       mono_error_cleanup (&error); /* just probing, ignore error */
                        return FALSE;
+               }
 
                return mono_defaults.methodhandle_class == handle_class;
        }
@@ -5836,12 +6076,14 @@ ves_icall_System_Reflection_Module_ResolveTypeToken (MonoImage *image, guint32 t
 
        if (image_is_dynamic (image)) {
                if ((table == MONO_TABLE_TYPEDEF) || (table == MONO_TABLE_TYPEREF)) {
-                       klass = (MonoClass *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL);
+                       klass = (MonoClass *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL, &error);
+                       mono_error_cleanup (&error);
                        return klass ? &klass->byval_arg : NULL;
                }
 
                init_generic_context_from_args (&context, type_args, method_args);
-               klass = (MonoClass *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context);
+               klass = (MonoClass *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context, &error);
+               mono_error_cleanup (&error);
                return klass ? &klass->byval_arg : NULL;
        }
 
@@ -5884,8 +6126,11 @@ ves_icall_System_Reflection_Module_ResolveMethodToken (MonoImage *image, guint32
        }
 
        if (image_is_dynamic (image)) {
-               if (table == MONO_TABLE_METHOD)
-                       return (MonoMethod *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL);
+               if (table == MONO_TABLE_METHOD) {
+                       method = (MonoMethod *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL, &error);
+                       mono_error_cleanup (&error);
+                       return method;
+               }
 
                if ((table == MONO_TABLE_MEMBERREF) && !(mono_memberref_is_method (image, token))) {
                        *resolve_error = ResolveTokenError_BadTable;
@@ -5893,7 +6138,9 @@ ves_icall_System_Reflection_Module_ResolveMethodToken (MonoImage *image, guint32
                }
 
                init_generic_context_from_args (&context, type_args, method_args);
-               return (MonoMethod *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context);
+               method = (MonoMethod *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context, &error);
+               mono_error_cleanup (&error);
+               return method;
        }
 
        if ((index <= 0) || (index > image->tables [table].rows)) {
@@ -5913,23 +6160,27 @@ ves_icall_System_Reflection_Module_ResolveMethodToken (MonoImage *image, guint32
 }
 
 ICALL_EXPORT MonoString*
-ves_icall_System_Reflection_Module_ResolveStringToken (MonoImage *image, guint32 token, MonoResolveTokenError *error)
+ves_icall_System_Reflection_Module_ResolveStringToken (MonoImage *image, guint32 token, MonoResolveTokenError *resolve_error)
 {
+       MonoError error;
        int index = mono_metadata_token_index (token);
 
-       *error = ResolveTokenError_Other;
+       *resolve_error = ResolveTokenError_Other;
 
        /* Validate token */
        if (mono_metadata_token_code (token) != MONO_TOKEN_STRING) {
-               *error = ResolveTokenError_BadTable;
+               *resolve_error = ResolveTokenError_BadTable;
                return NULL;
        }
 
-       if (image_is_dynamic (image))
-               return (MonoString *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL);
+       if (image_is_dynamic (image)) {
+               MonoString * result = (MonoString *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL, &error);
+               mono_error_cleanup (&error);
+               return result;
+       }
 
        if ((index <= 0) || (index >= image->heap_us.size)) {
-               *error = ResolveTokenError_OutOfRange;
+               *resolve_error = ResolveTokenError_OutOfRange;
                return NULL;
        }
 
@@ -5957,8 +6208,11 @@ ves_icall_System_Reflection_Module_ResolveFieldToken (MonoImage *image, guint32
        }
 
        if (image_is_dynamic (image)) {
-               if (table == MONO_TABLE_FIELD)
-                       return (MonoClassField *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL);
+               if (table == MONO_TABLE_FIELD) {
+                       field = (MonoClassField *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, NULL, &error);
+                       mono_error_cleanup (&error);
+                       return field;
+               }
 
                if (mono_memberref_is_method (image, token)) {
                        *resolve_error = ResolveTokenError_BadTable;
@@ -5966,7 +6220,9 @@ ves_icall_System_Reflection_Module_ResolveFieldToken (MonoImage *image, guint32
                }
 
                init_generic_context_from_args (&context, type_args, method_args);
-               return (MonoClassField *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context);
+               field = (MonoClassField *)mono_lookup_dynamic_token_class (image, token, FALSE, NULL, &context, &error);
+               mono_error_cleanup (&error);
+               return field;
        }
 
        if ((index <= 0) || (index > image->tables [table].rows)) {
@@ -6002,7 +6258,7 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
                MonoType *t = ves_icall_System_Reflection_Module_ResolveTypeToken (image, token, type_args, method_args, error);
                if (t) {
                        ret = (MonoObject*) mono_type_get_object_checked (mono_domain_get (), t, &merror);
-                       mono_error_raise_exception (&merror);
+                       mono_error_set_pending_exception (&merror);
 
                        return ret;
                }
@@ -6014,7 +6270,7 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
                MonoMethod *m = ves_icall_System_Reflection_Module_ResolveMethodToken (image, token, type_args, method_args, error);
                if (m) {
                        ret = (MonoObject*)mono_method_get_object_checked (mono_domain_get (), m, m->klass, &merror);
-                       mono_error_raise_exception (&merror);
+                       mono_error_set_pending_exception (&merror);
 
                        return ret;
                } else
@@ -6024,7 +6280,7 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
                MonoClassField *f = ves_icall_System_Reflection_Module_ResolveFieldToken (image, token, type_args, method_args, error);
                if (f) {
                        ret =(MonoObject*)mono_field_get_object_checked (mono_domain_get (), f->parent, f, &merror);
-                       mono_error_raise_exception (&merror);
+                       mono_error_set_pending_exception (&merror);
                        return ret;
                }
                else
@@ -6035,7 +6291,7 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
                        MonoMethod *m = ves_icall_System_Reflection_Module_ResolveMethodToken (image, token, type_args, method_args, error);
                        if (m) {
                                ret = (MonoObject*)mono_method_get_object_checked (mono_domain_get (), m, m->klass, &merror);
-                               mono_error_raise_exception (&merror);
+                               mono_error_set_pending_exception (&merror);
 
                                return ret;
                        } else
@@ -6045,7 +6301,7 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
                        MonoClassField *f = ves_icall_System_Reflection_Module_ResolveFieldToken (image, token, type_args, method_args, error);
                        if (f) {
                                ret = (MonoObject*)mono_field_get_object_checked (mono_domain_get (), f->parent, f, &merror);
-                               mono_error_raise_exception (&merror);
+                               mono_error_set_pending_exception (&merror);
                                return ret;
                        }
                        else
@@ -6061,8 +6317,9 @@ ves_icall_System_Reflection_Module_ResolveMemberToken (MonoImage *image, guint32
 }
 
 ICALL_EXPORT MonoArray*
-ves_icall_System_Reflection_Module_ResolveSignature (MonoImage *image, guint32 token, MonoResolveTokenError *error)
+ves_icall_System_Reflection_Module_ResolveSignature (MonoImage *image, guint32 token, MonoResolveTokenError *resolve_error)
 {
+       MonoError error;
        int table = mono_metadata_token_table (token);
        int idx = mono_metadata_token_index (token);
        MonoTableInfo *tables = image->tables;
@@ -6070,7 +6327,7 @@ ves_icall_System_Reflection_Module_ResolveSignature (MonoImage *image, guint32 t
        const char *ptr;
        MonoArray *res;
 
-       *error = ResolveTokenError_OutOfRange;
+       *resolve_error = ResolveTokenError_OutOfRange;
 
        /* FIXME: Support other tables ? */
        if (table != MONO_TABLE_STANDALONESIG)
@@ -6087,7 +6344,9 @@ ves_icall_System_Reflection_Module_ResolveSignature (MonoImage *image, guint32 t
        ptr = mono_metadata_blob_heap (image, sig);
        len = mono_metadata_decode_blob_size (ptr, &ptr);
 
-       res = mono_array_new (mono_domain_get (), mono_defaults.byte_class, len);
+       res = mono_array_new_checked (mono_domain_get (), mono_defaults.byte_class, len, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        memcpy (mono_array_addr (res, guint8, 0), ptr, len);
        return res;
 }
@@ -6118,7 +6377,7 @@ ves_icall_ModuleBuilder_create_modified_type (MonoReflectionTypeBuilder *tb, Mon
                        g_free (str);
 
                        ret = mono_type_get_object_checked (mono_object_domain (tb), &klass->this_arg, &error);
-                       mono_error_raise_exception (&error);
+                       mono_error_set_pending_exception (&error);
 
                        return ret;
                case '*':
@@ -6156,7 +6415,7 @@ ves_icall_ModuleBuilder_create_modified_type (MonoReflectionTypeBuilder *tb, Mon
        g_free (str);
 
        ret = mono_type_get_object_checked (mono_object_domain (tb), &klass->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -6199,7 +6458,7 @@ ves_icall_Type_make_array_type (MonoReflectionType *type, int rank)
 
        klass = mono_class_from_mono_type (type->type);
        check_for_invalid_type (klass, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        if (rank == 0) //single dimentional array
                aklass = mono_array_class_get (klass, 1);
@@ -6207,7 +6466,7 @@ ves_icall_Type_make_array_type (MonoReflectionType *type, int rank)
                aklass = mono_bounded_array_class_get (klass, rank, TRUE);
 
        ret = mono_type_get_object_checked (mono_object_domain (type), &aklass->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -6221,12 +6480,15 @@ ves_icall_Type_make_byref_type (MonoReflectionType *type)
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
        check_for_invalid_type (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        ret = mono_type_get_object_checked (mono_object_domain (type), &klass->this_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -6240,14 +6502,16 @@ ves_icall_Type_MakePointerType (MonoReflectionType *type)
 
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
        check_for_invalid_type (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        pklass = mono_ptr_class_get (type->type);
 
        ret = mono_type_get_object_checked (mono_object_domain (type), &pklass->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -6263,17 +6527,31 @@ ves_icall_System_Delegate_CreateDelegate_internal (MonoReflectionType *type, Mon
        MonoMethod *method = info->method;
 
        mono_class_init_checked (delegate_class, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
-       mono_assert (delegate_class->parent == mono_defaults.multicastdelegate_class);
+       if (!(delegate_class->parent == mono_defaults.multicastdelegate_class)) {
+               /* FIXME improve this exception message */
+               mono_error_set_execution_engine (&error, "file %s: line %d (%s): assertion failed: (%s)", __FILE__, __LINE__,
+                                                __func__,
+                                                "delegate_class->parent == mono_defaults.multicastdelegate_class");
+               mono_error_set_pending_exception (&error);
+               return NULL;
+       }
 
        if (mono_security_core_clr_enabled ()) {
-               if (!mono_security_core_clr_ensure_delegate_creation (method, throwOnBindFailure))
+               if (!mono_security_core_clr_ensure_delegate_creation (method, &error)) {
+                       if (throwOnBindFailure)
+                               mono_error_set_pending_exception (&error);
+                       else
+                               mono_error_cleanup (&error);
                        return NULL;
+               }
        }
 
        delegate = mono_object_new_checked (mono_object_domain (type), delegate_class, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (method_is_dynamic (method)) {
                /* Creating a trampoline would leak memory */
@@ -6281,8 +6559,10 @@ ves_icall_System_Delegate_CreateDelegate_internal (MonoReflectionType *type, Mon
        } else {
                if (target && method->flags & METHOD_ATTRIBUTE_VIRTUAL && method->klass != mono_object_class (target))
                        method = mono_object_get_virtual_method (target, method);
-               func = mono_create_ftnptr (mono_domain_get (),
-                       mono_runtime_create_jump_trampoline (mono_domain_get (), method, TRUE));
+               gpointer trampoline = mono_runtime_create_jump_trampoline (mono_domain_get (), method, TRUE, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
+               func = mono_create_ftnptr (mono_domain_get (), trampoline);
        }
 
        mono_delegate_ctor_with_method (delegate, target, func, method);
@@ -6299,7 +6579,9 @@ ves_icall_System_Delegate_AllocDelegateLike_internal (MonoDelegate *delegate)
        g_assert (mono_class_has_parent (mono_object_class (delegate), mono_defaults.multicastdelegate_class));
 
        ret = (MonoMulticastDelegate*) mono_object_new_checked (mono_object_domain (delegate), mono_object_class (delegate), &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
        ret->delegate.invoke_impl = mono_runtime_create_delegate_trampoline (mono_object_class (delegate));
 
        return ret;
@@ -6311,7 +6593,7 @@ ves_icall_System_Delegate_GetVirtualMethod_internal (MonoDelegate *delegate)
        MonoReflectionMethod *ret = NULL;
        MonoError error;
        ret = mono_method_get_object_checked (mono_domain_get (), mono_object_get_virtual_method (delegate->target, delegate->method), mono_object_class (delegate->target), &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return ret;
 }
 
@@ -6421,7 +6703,9 @@ ves_icall_Remoting_RealProxy_GetTransparentProxy (MonoObject *this_obj, MonoStri
        MonoClass *klass;
 
        res = mono_object_new_checked (domain, mono_defaults.transparent_proxy_class, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
+
        tp = (MonoTransparentProxy*) res;
        
        MONO_OBJECT_SETREF (tp, rp, rp);
@@ -6435,7 +6719,11 @@ ves_icall_Remoting_RealProxy_GetTransparentProxy (MonoObject *this_obj, MonoStri
                return NULL;
        }
 
-       tp->custom_type_info = (mono_object_isinst (this_obj, mono_defaults.iremotingtypeinfo_class) != NULL);
+       tp->custom_type_info = (mono_object_isinst_checked (this_obj, mono_defaults.iremotingtypeinfo_class, &error) != NULL);
+       if (!is_ok (&error)) {
+               mono_error_set_pending_exception (&error);
+               return NULL;
+       }
        tp->remote_class = mono_remote_class (domain, class_name, klass, &error);
        if (!is_ok (&error)) {
                mono_error_set_pending_exception (&error);
@@ -6451,7 +6739,7 @@ ves_icall_Remoting_RealProxy_InternalGetProxyType (MonoTransparentProxy *tp)
 {
        MonoError error;
        MonoReflectionType *ret = mono_type_get_object_checked (mono_object_domain (tp), &tp->remote_class->proxy_class->byval_arg, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return ret;
 }
@@ -6482,7 +6770,7 @@ ves_icall_System_Environment_get_MachineName (void)
        if (GetComputerName (buf, (PDWORD) &len)) {
                MonoError error;
                result = mono_string_new_utf16_checked (mono_domain_get (), buf, len, &error);
-               mono_error_raise_exception (&error);
+               mono_error_set_pending_exception (&error);
        }
 
        g_free (buf);
@@ -6609,10 +6897,20 @@ char **environ;
 #endif
 #endif
 
+ICALL_EXPORT MonoArray *
+ves_icall_System_Environment_GetCoomandLineArgs (void)
+{
+       MonoError error;
+       MonoArray *result = mono_runtime_get_main_args_checked (&error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
 ICALL_EXPORT MonoArray *
 ves_icall_System_Environment_GetEnvironmentVariableNames (void)
 {
 #ifdef HOST_WIN32
+       MonoError error;
        MonoArray *names;
        MonoDomain *domain;
        MonoString *str;
@@ -6636,7 +6934,9 @@ ves_icall_System_Environment_GetEnvironmentVariableNames (void)
        }
 
        domain = mono_domain_get ();
-       names = mono_array_new (domain, mono_defaults.string_class, n);
+       names = mono_array_new_checked (domain, mono_defaults.string_class, n, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (env_strings) {
                n = 0;
@@ -6648,7 +6948,9 @@ ves_icall_System_Environment_GetEnvironmentVariableNames (void)
                                g_assert(equal_str);
                                MonoError error;
                                str = mono_string_new_utf16_checked (domain, env_string, equal_str-env_string, &error);
-                               mono_error_raise_exception (&error);
+                               if (mono_error_set_pending_exception (&error))
+                                       return NULL;
+
                                mono_array_setref (names, n, str);
                                n++;
                        }
@@ -6663,6 +6965,7 @@ ves_icall_System_Environment_GetEnvironmentVariableNames (void)
        return names;
 
 #else
+       MonoError error;
        MonoArray *names;
        MonoDomain *domain;
        MonoString *str;
@@ -6674,7 +6977,9 @@ ves_icall_System_Environment_GetEnvironmentVariableNames (void)
                ++ n;
 
        domain = mono_domain_get ();
-       names = mono_array_new (domain, mono_defaults.string_class, n);
+       names = mono_array_new_checked (domain, mono_defaults.string_class, n, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        n = 0;
        for (e = environ; *e != 0; ++ e) {
@@ -6792,7 +7097,7 @@ ves_icall_System_Environment_GetWindowsFolderPath (int folder)
                        ++ len;
                MonoError error;
                MonoString *res = mono_string_new_utf16_checked (mono_domain_get (), path, len, &error);
-               mono_error_raise_exception (&error);
+               mono_error_set_pending_exception (&error);
                return res;
        }
 #else
@@ -6837,18 +7142,24 @@ ves_icall_System_Environment_GetLogicalDrives (void)
        } while (*dname);
 
        dname = ptr;
-       result = mono_array_new (domain, mono_defaults.string_class, ndrives);
+       result = mono_array_new_checked (domain, mono_defaults.string_class, ndrives, &error);
+       if (mono_error_set_pending_exception (&error))
+               goto leave;
+
        ndrives = 0;
        do {
                len = 0;
                u16 = dname;
                while (*u16) { u16++; len ++; }
                drivestr = mono_string_new_utf16_checked (domain, dname, len, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       goto leave;
+
                mono_array_setref (result, ndrives++, drivestr);
                while (*dname++);
        } while (*dname);
 
+leave:
        if (ptr != buf)
                g_free (ptr);
 
@@ -7020,7 +7331,8 @@ ves_icall_Remoting_RemotingServices_GetVirtualMethod (
        method = rmethod->method;
        klass = mono_class_from_mono_type (rtype->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (MONO_CLASS_IS_INTERFACE (klass))
                return NULL;
@@ -7056,7 +7368,7 @@ ves_icall_Remoting_RemotingServices_GetVirtualMethod (
                return NULL;
 
        ret = mono_method_get_object_checked (mono_domain_get (), res, NULL, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return ret;
 }
 
@@ -7098,7 +7410,8 @@ ves_icall_System_Runtime_Activation_ActivationServices_AllocateUninitializedClas
        domain = mono_object_domain (type);
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (MONO_CLASS_IS_INTERFACE (klass) || (klass->flags & TYPE_ATTRIBUTE_ABSTRACT)) {
                mono_set_pending_exception (mono_get_exception_argument ("type", "Type cannot be instantiated"));
@@ -7107,7 +7420,9 @@ ves_icall_System_Runtime_Activation_ActivationServices_AllocateUninitializedClas
 
        if (klass->rank >= 1) {
                g_assert (klass->rank == 1);
-               return (MonoObject *) mono_array_new (domain, klass->element_class, 0);
+               ret = (MonoObject *) mono_array_new_checked (domain, klass->element_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return ret;
        } else {
                MonoVTable *vtable = mono_class_vtable_full (domain, klass, &error);
                if (!is_ok (&error)) {
@@ -7342,14 +7657,15 @@ ves_icall_System_Activator_CreateInstanceInternal (MonoReflectionType *type)
        domain = mono_object_domain (type);
        klass = mono_class_from_mono_type (type->type);
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (mono_class_is_nullable (klass))
                /* No arguments -> null */
                return NULL;
 
        result = mono_object_new_checked (domain, klass, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -7410,7 +7726,6 @@ ves_icall_MonoMethod_get_base_method (MonoReflectionMethod *m, gboolean definiti
                        */
                        MonoGenericContext *parent_inst = NULL;
                        if (mono_class_is_open_constructed_type (mono_class_get_type (parent))) {
-                               MonoError error;
                                parent = mono_class_inflate_generic_class_checked (parent, generic_inst, &error);
                                if (!mono_error_ok (&error)) {
                                        mono_error_set_pending_exception (&error);
@@ -7480,7 +7795,7 @@ ves_icall_MonoMethod_get_base_method (MonoReflectionMethod *m, gboolean definiti
                return m;
 
        ret = mono_method_get_object_checked (mono_domain_get (), result, NULL, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return ret;
 }
 
@@ -7602,12 +7917,16 @@ mono_ArgIterator_IntGetNextArgType (MonoArgIterator *iter)
 ICALL_EXPORT MonoObject*
 mono_TypedReference_ToObject (MonoTypedRef* tref)
 {
+       MonoError error;
+       MonoObject *result = NULL;
        if (MONO_TYPE_IS_REFERENCE (tref->type)) {
                MonoObject** objp = (MonoObject **)tref->value;
                return *objp;
        }
 
-       return mono_value_box (mono_domain_get (), tref->klass, tref->value);
+       result = mono_value_box_checked (mono_domain_get (), tref->klass, tref->value, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 ICALL_EXPORT MonoTypedRef
@@ -7675,7 +7994,7 @@ ves_icall_System_Runtime_InteropServices_Marshal_Prelink (MonoReflectionMethod *
        MonoError error;
 
        prelink_method (method->method, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 }
 
 ICALL_EXPORT void
@@ -7687,11 +8006,13 @@ ves_icall_System_Runtime_InteropServices_Marshal_PrelinkAll (MonoReflectionType
        gpointer iter = NULL;
 
        mono_class_init_checked (klass, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return;
 
        while ((m = mono_class_get_methods (klass, &iter))) {
                prelink_method (m, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return;
        }
 }
 
@@ -7730,7 +8051,8 @@ type_array_from_modifiers (MonoImage *image, MonoType *type, int optional, MonoE
        }
        if (!count)
                return NULL;
-       res = mono_array_new (mono_domain_get (), mono_defaults.systemtype_class, count);
+       res = mono_array_new_checked (mono_domain_get (), mono_defaults.systemtype_class, count, error);
+       return_val_if_nok (error, NULL);
        count = 0;
        for (i = 0; i < type->num_mods; ++i) {
                if ((optional && !type->modifiers [i].required) || (!optional && type->modifiers [i].required)) {
@@ -7786,7 +8108,7 @@ ves_icall_ParameterInfo_GetTypeModifiers (MonoReflectionParameter *param, MonoBo
                type = sig->params [pos];
 
        res = type_array_from_modifiers (image, type, optional, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -7815,7 +8137,7 @@ ves_icall_MonoPropertyInfo_GetTypeModifiers (MonoReflectionProperty *property, M
        if (!type)
                return NULL;
        res = type_array_from_modifiers (image, type, optional, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -7878,7 +8200,8 @@ custom_attrs_defined_internal (MonoObject *obj, MonoReflectionType *attr_type)
        gboolean found;
 
        mono_class_init_checked (attr_class, &error);
-       mono_error_raise_exception (&error);
+       if (mono_error_set_pending_exception (&error))
+               return FALSE;
 
        cinfo = mono_reflection_get_custom_attrs_info_checked (obj, &error);
        if (!is_ok (&error)) {
@@ -7902,7 +8225,8 @@ custom_attrs_get_by_type (MonoObject *obj, MonoReflectionType *attr_type)
 
        if (attr_class) {
                mono_class_init_checked (attr_class, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
        }
 
        res = mono_reflection_get_custom_attrs_by_type (obj, attr_class, &error);
@@ -7911,12 +8235,7 @@ custom_attrs_get_by_type (MonoObject *obj, MonoReflectionType *attr_type)
                return NULL;
        }
 
-       if (mono_loader_get_last_error ()) {
-               mono_set_pending_exception (mono_loader_error_prepare_exception (mono_loader_get_last_error ()));
-               return NULL;
-       } else {
-               return res;
-       }
+       return res;
 }
 
 ICALL_EXPORT MonoArray*
@@ -7957,26 +8276,13 @@ ves_icall_System_ComponentModel_Win32Exception_W32ErrorMessage (guint32 code)
                message = mono_string_new (mono_domain_get (), "Error looking up error string");
        } else {
                message = mono_string_new_utf16_checked (mono_domain_get (), buf, ret, &error);
-               mono_error_raise_exception (&error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
        }
        
        return message;
 }
 
-ICALL_EXPORT int
-ves_icall_System_StackFrame_GetILOffsetFromFile (MonoString *path, guint32 method_token, guint32 method_index, int native_offset)
-{
-       guint32 il_offset;
-       char *path_str = mono_string_to_utf8 (path);
-
-       if (!mono_seq_point_data_get_il_offset (path_str, method_token, method_index, native_offset, &il_offset))
-               il_offset = -1;
-
-       g_free (path_str);
-
-       return il_offset;
-}
-
 ICALL_EXPORT gpointer
 ves_icall_Microsoft_Win32_NativeMethods_GetCurrentProcess (void)
 {
index e5211176d8eeb390d84f797d0f4d036759316d82..959575f6a0a4a8c8996720693fd4a39d412b0c4a 100644 (file)
@@ -1,5 +1,6 @@
 /* 
  * Copyright 2015 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_METADATA_IMAGE_INTERNALS_H__
 #define __MONO_METADATA_IMAGE_INTERNALS_H__
index 8d877d3e3427c386994a8633ab8727243b327c72..7b1b4278315a2eddd8463dd5b6e86039efa3ed65 100644 (file)
@@ -9,6 +9,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
@@ -1080,13 +1081,13 @@ do_mono_image_load (MonoImage *image, MonoImageOpenStatus *status,
                goto done;
        }
 
-       if (image->loader == &pe_loader && !mono_verifier_verify_cli_data (image, &errors))
+       if (image->loader == &pe_loader && !image->metadata_only && !mono_verifier_verify_cli_data (image, &errors))
                goto invalid_image;
 
        if (!mono_image_load_cli_data (image))
                goto invalid_image;
 
-       if (image->loader == &pe_loader && !mono_verifier_verify_table_data (image, &errors))
+       if (image->loader == &pe_loader && !image->metadata_only && !mono_verifier_verify_table_data (image, &errors))
                goto invalid_image;
 
        mono_image_load_names (image);
index 2f4be6663ff503b84ec0f3f1983d4587fca2d875..e94b73d590cfe85fd055d00b341fc8d84198c924 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011-2012 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -613,7 +614,7 @@ jit_info_table_add (MonoDomain *domain, MonoJitInfoTable *volatile *table_ptr, M
                *table_ptr = new_table;
                mono_memory_barrier ();
                domain->num_jit_info_tables++;
-               mono_thread_hazardous_free_or_queue (table, (MonoHazardousFreeFunc)mono_jit_info_table_free, HAZARD_FREE_MAY_LOCK, HAZARD_FREE_SAFE_CTX);
+               mono_thread_hazardous_try_free (table, (MonoHazardousFreeFunc)mono_jit_info_table_free);
                table = new_table;
 
                goto restart;
@@ -691,7 +692,7 @@ mono_jit_info_free_or_queue (MonoDomain *domain, MonoJitInfo *ji)
        if (domain->num_jit_info_tables <= 1) {
                /* Can it actually happen that we only have one table
                   but ji is still hazardous? */
-               mono_thread_hazardous_free_or_queue (ji, g_free, HAZARD_FREE_MAY_LOCK, HAZARD_FREE_SAFE_CTX);
+               mono_thread_hazardous_try_free (ji, g_free);
        } else {
                domain->jit_info_free_queue = g_slist_prepend (domain->jit_info_free_queue, ji);
        }
index 56630da1eddbdf44b210c32f3670351a49b502e7..2922234965a5035b83acf0ce6b3f0f7b51d22f18 100644 (file)
@@ -17,6 +17,7 @@
  * TODO:
  *   This should keep track of the assembly versions that we are loading.
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <glib.h>
@@ -66,11 +67,6 @@ static guint32 memberref_sig_cache_size;
 static guint32 methods_size;
 static guint32 signatures_size;
 
-/*
- * This TLS variable contains the last type load error encountered by the loader.
- */
-MonoNativeTlsKey loader_error_thread_id;
-
 /*
  * This TLS variable holds how many times the current thread has acquired the loader 
  * lock.
@@ -102,7 +98,6 @@ mono_loader_init ()
                mono_os_mutex_init_recursive (&global_loader_data_mutex);
                loader_lock_inited = TRUE;
 
-               mono_native_tls_alloc (&loader_error_thread_id, NULL);
                mono_native_tls_alloc (&loader_lock_nest_id, NULL);
 
                mono_counters_init ();
@@ -124,7 +119,6 @@ mono_loader_cleanup (void)
 {
        dllmap_cleanup ();
 
-       mono_native_tls_free (loader_error_thread_id);
        mono_native_tls_free (loader_lock_nest_id);
 
        mono_coop_mutex_destroy (&loader_mutex);
@@ -132,281 +126,6 @@ mono_loader_cleanup (void)
        loader_lock_inited = FALSE;     
 }
 
-/*
- * Handling of type load errors should be done as follows:
- *
- *   If something could not be loaded, the loader should call one of the
- * mono_loader_set_error_XXX functions ()
- * with the appropriate arguments, then return NULL to report the failure. The error 
- * should be propagated until it reaches code which can throw managed exceptions. At that
- * point, an exception should be thrown based on the information returned by
- * mono_loader_get_last_error (). Then the error should be cleared by calling 
- * mono_loader_clear_error ().
- */
-
-static void
-set_loader_error (MonoLoaderError *error)
-{
-       mono_loader_clear_error ();
-       mono_native_tls_set_value (loader_error_thread_id, error);
-}
-
-/**
- * mono_loader_set_error_assembly_load:
- *
- * Set the loader error for this thread. 
- */
-void
-mono_loader_set_error_assembly_load (const char *assembly_name, gboolean ref_only)
-{
-       MonoLoaderError *error;
-
-       if (mono_loader_get_last_error ()) 
-               return;
-
-       error = g_new0 (MonoLoaderError, 1);
-       error->exception_type = MONO_EXCEPTION_FILE_NOT_FOUND;
-       error->assembly_name = g_strdup (assembly_name);
-       error->ref_only = ref_only;
-
-       /* 
-        * This is not strictly needed, but some (most) of the loader code still
-        * can't deal with load errors, and this message is more helpful than an
-        * assert.
-        */
-       if (ref_only)
-               mono_trace (G_LOG_LEVEL_WARNING, MONO_TRACE_ASSEMBLY, "Cannot resolve dependency to assembly '%s' because it has not been preloaded. When using the ReflectionOnly APIs, dependent assemblies must be pre-loaded or loaded on demand through the ReflectionOnlyAssemblyResolve event.", assembly_name);
-       else
-               mono_trace (G_LOG_LEVEL_WARNING, MONO_TRACE_ASSEMBLY, "Could not load file or assembly '%s' or one of its dependencies.", assembly_name);
-
-       set_loader_error (error);
-}
-
-/**
- * mono_loader_set_error_type_load:
- *
- * Set the loader error for this thread. 
- */
-void
-mono_loader_set_error_type_load (const char *class_name, const char *assembly_name)
-{
-       MonoLoaderError *error;
-
-       if (mono_loader_get_last_error ()) 
-               return;
-
-       error = g_new0 (MonoLoaderError, 1);
-       error->exception_type = MONO_EXCEPTION_TYPE_LOAD;
-       error->class_name = g_strdup (class_name);
-       error->assembly_name = g_strdup (assembly_name);
-
-       /* 
-        * This is not strictly needed, but some (most) of the loader code still
-        * can't deal with load errors, and this message is more helpful than an
-        * assert.
-        */
-       mono_trace_warning (MONO_TRACE_TYPE, "The class %s could not be loaded, used in %s", class_name, assembly_name);
-
-       set_loader_error (error);
-}
-
-/*
- * mono_loader_set_error_method_load:
- *
- *   Set the loader error for this thread. MEMBER_NAME should point to a string
- * inside metadata.
- */
-void
-mono_loader_set_error_method_load (const char *class_name, const char *member_name)
-{
-       MonoLoaderError *error;
-
-       /* FIXME: Store the signature as well */
-       if (mono_loader_get_last_error ())
-               return;
-
-       error = g_new0 (MonoLoaderError, 1);
-       error->exception_type = MONO_EXCEPTION_MISSING_METHOD;
-       error->class_name = g_strdup (class_name);
-       error->member_name = member_name;
-
-       set_loader_error (error);
-}
-
-/*
- * mono_loader_set_error_field_load:
- *
- * Set the loader error for this thread. MEMBER_NAME should point to a string
- * inside metadata.
- */
-void
-mono_loader_set_error_field_load (MonoClass *klass, const char *member_name)
-{
-       MonoLoaderError *error;
-
-       /* FIXME: Store the signature as well */
-       if (mono_loader_get_last_error ())
-               return;
-
-       error = g_new0 (MonoLoaderError, 1);
-       error->exception_type = MONO_EXCEPTION_MISSING_FIELD;
-       error->klass = klass;
-       error->member_name = member_name;
-
-       set_loader_error (error);
-}
-
-/*
- * mono_loader_set_error_bad_image:
- *
- * Set the loader error for this thread. 
- */
-void
-mono_loader_set_error_bad_image (char *msg)
-{
-       MonoLoaderError *error;
-
-       if (mono_loader_get_last_error ())
-               return;
-
-       error = g_new0 (MonoLoaderError, 1);
-       error->exception_type = MONO_EXCEPTION_BAD_IMAGE;
-       error->msg = msg;
-
-       set_loader_error (error);
-}      
-
-
-/*
- * mono_loader_get_last_error:
- *
- *   Returns information about the last type load exception encountered by the loader, or
- * NULL. After use, the exception should be cleared by calling mono_loader_clear_error.
- */
-MonoLoaderError*
-mono_loader_get_last_error (void)
-{
-       return (MonoLoaderError*)mono_native_tls_get_value (loader_error_thread_id);
-}
-
-void
-mono_loader_assert_no_error (void)
-{
-       MonoLoaderError *error = mono_loader_get_last_error ();
-
-       if (error) {
-               g_print ("Unhandled loader error: %x, %s %s %s\n", error->exception_type, error->msg, error->assembly_name, error->class_name);
-               g_assert_not_reached ();
-       }
-}
-
-/**
- * mono_loader_clear_error:
- *
- * Disposes any loader error messages on this thread
- */
-void
-mono_loader_clear_error (void)
-{
-       MonoLoaderError *ex = (MonoLoaderError*)mono_native_tls_get_value (loader_error_thread_id);
-
-       if (ex) {
-               g_free (ex->class_name);
-               g_free (ex->assembly_name);
-               g_free (ex->msg);
-               g_free (ex);
-
-               mono_native_tls_set_value (loader_error_thread_id, NULL);
-       }
-}
-
-/**
- * mono_loader_error_prepare_exception:
- * @error: The MonoLoaderError to turn into an exception
- *
- * This turns a MonoLoaderError into an exception that can be thrown
- * and resets the Mono Loader Error state during this process.
- *
- */
-MonoException *
-mono_loader_error_prepare_exception (MonoLoaderError *error)
-{
-       MonoException *ex = NULL;
-
-       switch (error->exception_type) {
-       case MONO_EXCEPTION_TYPE_LOAD: {
-               char *cname = g_strdup (error->class_name);
-               char *aname = g_strdup (error->assembly_name);
-               MonoString *class_name;
-               
-               mono_loader_clear_error ();
-               
-               class_name = mono_string_new (mono_domain_get (), cname);
-
-               ex = mono_get_exception_type_load (class_name, aname);
-               g_free (cname);
-               g_free (aname);
-               break;
-        }
-       case MONO_EXCEPTION_MISSING_METHOD: {
-               char *cname = g_strdup (error->class_name);
-               char *aname = g_strdup (error->member_name);
-               
-               mono_loader_clear_error ();
-               ex = mono_get_exception_missing_method (cname, aname);
-               g_free (cname);
-               g_free (aname);
-               break;
-       }
-               
-       case MONO_EXCEPTION_MISSING_FIELD: {
-               char *class_name;
-               char *cmembername = g_strdup (error->member_name);
-               if (error->klass)
-                       class_name = mono_type_get_full_name (error->klass);
-               else
-                       class_name = g_strdup ("");
-
-               mono_loader_clear_error ();
-               
-               ex = mono_get_exception_missing_field (class_name, cmembername);
-               g_free (class_name);
-               g_free (cmembername);
-               break;
-        }
-       
-       case MONO_EXCEPTION_FILE_NOT_FOUND: {
-               char *msg;
-               char *filename;
-
-               if (error->ref_only)
-                       msg = g_strdup_printf ("Cannot resolve dependency to assembly '%s' because it has not been preloaded. When using the ReflectionOnly APIs, dependent assemblies must be pre-loaded or loaded on demand through the ReflectionOnlyAssemblyResolve event.", error->assembly_name);
-               else
-                       msg = g_strdup_printf ("Could not load file or assembly '%s' or one of its dependencies.", error->assembly_name);
-               filename = g_strdup (error->assembly_name);
-               /* Has to call this before calling anything which might call mono_class_init () */
-               mono_loader_clear_error ();
-               ex = mono_get_exception_file_not_found2 (msg, mono_string_new (mono_domain_get (), filename));
-               g_free (msg);
-               g_free (filename);
-               break;
-       }
-
-       case MONO_EXCEPTION_BAD_IMAGE: {
-               char *msg = g_strdup (error->msg);
-               mono_loader_clear_error ();
-               ex = mono_get_exception_bad_image_format (msg);
-               g_free (msg);
-               break;
-       }
-
-       default:
-               g_assert_not_reached ();
-       }
-
-       return ex;
-}
-
 /*
  * find_cached_memberref_sig:
  *
@@ -528,7 +247,6 @@ field_from_memberref (MonoImage *image, guint32 token, MonoClass **retklass,
        field = mono_class_get_field_from_name_full (klass, fname, sig_type);
 
        if (!field) {
-               mono_loader_assert_no_error ();
                mono_error_set_field_load (error, klass, fname, "Could not find field '%s'", fname);
        }
 
@@ -563,7 +281,9 @@ mono_field_from_token_checked (MonoImage *image, guint32 token, MonoClass **retk
                MonoClass *handle_class;
 
                *retklass = NULL;
-               result = (MonoClassField *)mono_lookup_dynamic_token_class (image, token, TRUE, &handle_class, context);
+               MonoError inner_error;
+               result = (MonoClassField *)mono_lookup_dynamic_token_class (image, token, TRUE, &handle_class, context, &inner_error);
+               mono_error_cleanup (&inner_error);
                // This checks the memberref type as well
                if (!result || handle_class != mono_defaults.fieldhandle_class) {
                        mono_error_set_bad_image (error, image, "Bad field token 0x%08x", token);
@@ -580,7 +300,6 @@ mono_field_from_token_checked (MonoImage *image, guint32 token, MonoClass **retk
 
        if (mono_metadata_token_table (token) == MONO_TABLE_MEMBERREF) {
                field = field_from_memberref (image, token, retklass, context, error);
-               mono_loader_assert_no_error ();
        } else {
                type = mono_metadata_typedef_from_field (image, mono_metadata_token_index (token));
                if (!type) {
@@ -596,10 +315,7 @@ mono_field_from_token_checked (MonoImage *image, guint32 token, MonoClass **retk
                        *retklass = k;
                field = mono_class_get_field (k, token);
                if (!field) {
-                       if (mono_loader_get_last_error ())
-                               mono_error_set_from_loader_error (error);
-                       else
-                               mono_error_set_bad_image (error, image, "Could not resolve field token 0x%08x", token);
+                       mono_error_set_bad_image (error, image, "Could not resolve field token 0x%08x", token);
                }
        }
 
@@ -609,7 +325,6 @@ mono_field_from_token_checked (MonoImage *image, guint32 token, MonoClass **retk
                mono_image_unlock (image);
        }
 
-       mono_loader_assert_no_error ();
        return field;
 }
 
@@ -874,27 +589,31 @@ mono_inflate_generic_signature (MonoMethodSignature *sig, MonoGenericContext *co
 static MonoMethodHeader*
 inflate_generic_header (MonoMethodHeader *header, MonoGenericContext *context, MonoError *error)
 {
-       MonoMethodHeader *res;
-       int i;
-       res = (MonoMethodHeader *)g_malloc0 (MONO_SIZEOF_METHOD_HEADER + sizeof (gpointer) * header->num_locals);
+       size_t locals_size = sizeof (gpointer) * header->num_locals;
+       size_t clauses_size = header->num_clauses * sizeof (MonoExceptionClause);
+       size_t header_size = MONO_SIZEOF_METHOD_HEADER + locals_size + clauses_size; 
+       MonoMethodHeader *res = (MonoMethodHeader *)g_malloc0 (header_size);
+       res->num_locals = header->num_locals;
+       res->clauses = (MonoExceptionClause *) &res->locals [res->num_locals] ;
+       memcpy (res->clauses, header->clauses, clauses_size);
+
        res->code = header->code;
        res->code_size = header->code_size;
        res->max_stack = header->max_stack;
        res->num_clauses = header->num_clauses;
        res->init_locals = header->init_locals;
-       res->num_locals = header->num_locals;
-       res->clauses = header->clauses;
+
+       res->is_transient = TRUE;
 
        mono_error_init (error);
 
-       for (i = 0; i < header->num_locals; ++i) {
+       for (int i = 0; i < header->num_locals; ++i) {
                res->locals [i] = mono_class_inflate_generic_type_checked (header->locals [i], context, error);
                if (!is_ok (error))
                        goto fail;
        }
        if (res->num_clauses) {
-               res->clauses = (MonoExceptionClause *)g_memdup (header->clauses, sizeof (MonoExceptionClause) * res->num_clauses);
-               for (i = 0; i < header->num_clauses; ++i) {
+               for (int i = 0; i < header->num_clauses; ++i) {
                        MonoExceptionClause *clause = &res->clauses [i];
                        if (clause->flags != MONO_EXCEPTION_CLAUSE_NONE)
                                continue;
@@ -1158,19 +877,14 @@ method_from_memberref (MonoImage *image, guint32 idx, MonoGenericContext *typesp
                g_free (msig);
                msig = g_string_free (s, FALSE);
 
-               if (mono_loader_get_last_error ()) /* FIXME find_method and mono_method_search_in_array_class can leak a loader error */
-                       mono_error_set_from_loader_error (error);
-               else
-                       mono_error_set_method_load (error, klass, mname, "Could not find method %s", msig);
+               mono_error_set_method_load (error, klass, mname, "Could not find method %s", msig);
 
                g_free (msig);
        }
 
-       mono_loader_assert_no_error ();
        return method;
 
 fail:
-       mono_loader_assert_no_error ();
        g_assert (!mono_error_ok (error));
        return NULL;
 }
@@ -1236,7 +950,6 @@ method_from_methodspec (MonoImage *image, MonoGenericContext *context, guint32 i
        new_context.method_inst = inst;
 
        method = mono_class_inflate_generic_method_full_checked (method, klass, &new_context, error);
-       mono_loader_assert_no_error ();
        return method;
 }
 
@@ -1873,8 +1586,8 @@ mono_get_method_from_token (MonoImage *image, guint32 token, MonoClass *klass,
        if (image_is_dynamic (image)) {
                MonoClass *handle_class;
 
-               result = (MonoMethod *)mono_lookup_dynamic_token_class (image, token, TRUE, &handle_class, context);
-               mono_loader_assert_no_error ();
+               result = (MonoMethod *)mono_lookup_dynamic_token_class (image, token, TRUE, &handle_class, context, error);
+               mono_error_assert_ok (error);
 
                // This checks the memberref type as well
                if (result && handle_class != mono_defaults.methodhandle_class) {
@@ -1945,7 +1658,6 @@ mono_get_method_from_token (MonoImage *image, guint32 token, MonoClass *klass,
         */
        if (*sig & 0x10) {
                generic_container = mono_metadata_load_generic_params (image, token, container);
-               mono_loader_assert_no_error (); /* FIXME don't swallow this error. */
        }
        if (generic_container) {
                result->is_generic = TRUE;
@@ -1980,7 +1692,6 @@ mono_get_method_from_token (MonoImage *image, guint32 token, MonoClass *klass,
        if (generic_container)
                mono_method_set_generic_container (result, generic_container);
 
-       mono_loader_assert_no_error ();
        return result;
 }
 
@@ -2827,20 +2538,7 @@ mono_method_get_header_checked (MonoMethod *method, MonoError *error)
                        return NULL;
                }
 
-               mono_image_lock (img);
-
-               if (imethod->header) {
-                       mono_metadata_free_mh (iheader);
-                       mono_image_unlock (img);
-                       return imethod->header;
-               }
-
-               mono_memory_barrier ();
-               imethod->header = iheader;
-
-               mono_image_unlock (img);
-
-               return imethod->header;
+               return iheader;
        }
 
        if (method->wrapper_type != MONO_WRAPPER_NONE || method->sre_method) {
index 18b52ae2b82d58b68edd3419d411539592f567f9..e01f8be31d67a836e5f8c9e0b7bcffb725de557f 100644 (file)
@@ -10,6 +10,7 @@
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * (C) 2003 PT Cakram Datalingga Duaribu  http://www.cdl2000.com
  * Copyright (C) 2012 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -91,11 +92,13 @@ region_name_locator (const void *a, const void *b)
 }
 
 static MonoArray*
-create_group_sizes_array (const gint *gs, gint ml)
+create_group_sizes_array (const gint *gs, gint ml, MonoError *error)
 {
        MonoArray *ret;
        int i, len = 0;
 
+       mono_error_init (error);
+
        for (i = 0; i < ml; i++) {
                if (gs [i] == -1)
                        break;
@@ -103,7 +106,8 @@ create_group_sizes_array (const gint *gs, gint ml)
        }
        
        ret = mono_array_new_cached (mono_domain_get (),
-                       mono_get_int32_class (), len);
+                                    mono_get_int32_class (), len, error);
+       return_val_if_nok (error, NULL);
 
        for(i = 0; i < len; i++)
                mono_array_set (ret, gint32, i, gs [i]);
@@ -112,18 +116,21 @@ create_group_sizes_array (const gint *gs, gint ml)
 }
 
 static MonoArray*
-create_names_array_idx (const guint16 *names, int ml)
+create_names_array_idx (const guint16 *names, int ml, MonoError *error)
 {
        MonoArray *ret;
        MonoDomain *domain;
        int i;
 
+       mono_error_init (error);
+
        if (names == NULL)
                return NULL;
 
        domain = mono_domain_get ();
 
-       ret = mono_array_new_cached (mono_domain_get (), mono_get_string_class (), ml);
+       ret = mono_array_new_cached (mono_domain_get (), mono_get_string_class (), ml, error);
+       return_val_if_nok (error, NULL);
 
        for(i = 0; i < ml; i++)
                mono_array_setref (ret, i, mono_string_new (domain, idx2string (names [i])));
@@ -132,12 +139,14 @@ create_names_array_idx (const guint16 *names, int ml)
 }
 
 static MonoArray*
-create_names_array_idx_dynamic (const guint16 *names, int ml)
+create_names_array_idx_dynamic (const guint16 *names, int ml, MonoError *error)
 {
        MonoArray *ret;
        MonoDomain *domain;
        int i, len = 0;
 
+       mono_error_init (error);
+
        if (names == NULL)
                return NULL;
 
@@ -149,7 +158,8 @@ create_names_array_idx_dynamic (const guint16 *names, int ml)
                len++;
        }
 
-       ret = mono_array_new_cached (mono_domain_get (), mono_get_string_class (), len);
+       ret = mono_array_new_cached (mono_domain_get (), mono_get_string_class (), len, error);
+       return_val_if_nok (error, NULL);
 
        for(i = 0; i < len; i++)
                mono_array_setref (ret, i, mono_string_new (domain, idx2string (names [i])));
@@ -160,6 +170,7 @@ create_names_array_idx_dynamic (const guint16 *names, int ml)
 MonoBoolean
 ves_icall_System_Globalization_CalendarData_fill_calendar_data (MonoCalendarData *this_obj, MonoString *name, gint32 calendar_index)
 {
+       MonoError error;
        MonoDomain *domain;
        const DateTimeFormatEntry *dfe;
        const CultureInfoNameEntry *ne;
@@ -180,24 +191,52 @@ ves_icall_System_Globalization_CalendarData_fill_calendar_data (MonoCalendarData
        domain = mono_domain_get ();
 
        MONO_OBJECT_SETREF (this_obj, NativeName, mono_string_new (domain, idx2string (ci->nativename)));
-       MONO_OBJECT_SETREF (this_obj, ShortDatePatterns, create_names_array_idx_dynamic (dfe->short_date_patterns,
-                       NUM_SHORT_DATE_PATTERNS));
-       MONO_OBJECT_SETREF (this_obj, YearMonthPatterns, create_names_array_idx_dynamic (dfe->year_month_patterns,
-                       NUM_YEAR_MONTH_PATTERNS));
+       MonoArray *short_date_patterns = create_names_array_idx_dynamic (dfe->short_date_patterns,
+                                                                        NUM_SHORT_DATE_PATTERNS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, ShortDatePatterns, short_date_patterns);
+       MonoArray *year_month_patterns =create_names_array_idx_dynamic (dfe->year_month_patterns,
+                                                                       NUM_YEAR_MONTH_PATTERNS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, YearMonthPatterns, year_month_patterns);
+
+       MonoArray *long_date_patterns = create_names_array_idx_dynamic (dfe->long_date_patterns,
+                                                                       NUM_LONG_DATE_PATTERNS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, LongDatePatterns, long_date_patterns);
 
-       MONO_OBJECT_SETREF (this_obj, LongDatePatterns, create_names_array_idx_dynamic (dfe->long_date_patterns,
-                       NUM_LONG_DATE_PATTERNS));
        MONO_OBJECT_SETREF (this_obj, MonthDayPattern, mono_string_new (domain, idx2string (dfe->month_day_pattern)));
 
-       MONO_OBJECT_SETREF (this_obj, DayNames, create_names_array_idx (dfe->day_names, NUM_DAYS));
-       MONO_OBJECT_SETREF (this_obj, AbbreviatedDayNames, create_names_array_idx (dfe->abbreviated_day_names, 
-                       NUM_DAYS));
-       MONO_OBJECT_SETREF (this_obj, SuperShortDayNames, create_names_array_idx (dfe->shortest_day_names, NUM_DAYS));
-       MONO_OBJECT_SETREF (this_obj, MonthNames, create_names_array_idx (dfe->month_names, NUM_MONTHS));
-       MONO_OBJECT_SETREF (this_obj, AbbreviatedMonthNames, create_names_array_idx (dfe->abbreviated_month_names,
-                       NUM_MONTHS));
-       MONO_OBJECT_SETREF (this_obj, GenitiveMonthNames, create_names_array_idx (dfe->month_genitive_names, NUM_MONTHS));
-       MONO_OBJECT_SETREF (this_obj, GenitiveAbbreviatedMonthNames, create_names_array_idx (dfe->abbreviated_month_genitive_names, NUM_MONTHS));
+       MonoArray *day_names = create_names_array_idx (dfe->day_names, NUM_DAYS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, DayNames, day_names);
+
+       MonoArray *abbr_day_names = create_names_array_idx (dfe->abbreviated_day_names, 
+                                                           NUM_DAYS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, AbbreviatedDayNames, abbr_day_names);
+
+       MonoArray *ss_day_names = create_names_array_idx (dfe->shortest_day_names, NUM_DAYS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, SuperShortDayNames, ss_day_names);
+
+       MonoArray *month_names = create_names_array_idx (dfe->month_names, NUM_MONTHS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, MonthNames, month_names);
+
+       MonoArray *abbr_mon_names = create_names_array_idx (dfe->abbreviated_month_names,
+                                                           NUM_MONTHS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, AbbreviatedMonthNames, abbr_mon_names);
+
+       
+       MonoArray *gen_month_names = create_names_array_idx (dfe->month_genitive_names, NUM_MONTHS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, GenitiveMonthNames, gen_month_names);
+
+       MonoArray *gen_abbr_mon_names = create_names_array_idx (dfe->abbreviated_month_genitive_names, NUM_MONTHS, &error);
+       return_val_and_set_pending_if_nok (&error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, GenitiveAbbreviatedMonthNames, gen_abbr_mon_names);
 
        return TRUE;
 }
@@ -205,6 +244,7 @@ ves_icall_System_Globalization_CalendarData_fill_calendar_data (MonoCalendarData
 void
 ves_icall_System_Globalization_CultureData_fill_culture_data (MonoCultureData *this_obj, gint32 datetime_index)
 {
+       MonoError error;
        MonoDomain *domain;
        const DateTimeFormatEntry *dfe;
 
@@ -217,10 +257,18 @@ ves_icall_System_Globalization_CultureData_fill_culture_data (MonoCultureData *t
        MONO_OBJECT_SETREF (this_obj, AMDesignator, mono_string_new (domain, idx2string (dfe->am_designator)));
        MONO_OBJECT_SETREF (this_obj, PMDesignator, mono_string_new (domain, idx2string (dfe->pm_designator)));
        MONO_OBJECT_SETREF (this_obj, TimeSeparator, mono_string_new (domain, idx2string (dfe->time_separator)));
-       MONO_OBJECT_SETREF (this_obj, LongTimePatterns, create_names_array_idx_dynamic (dfe->long_time_patterns,
-                       NUM_LONG_TIME_PATTERNS));
-       MONO_OBJECT_SETREF (this_obj, ShortTimePatterns, create_names_array_idx_dynamic (dfe->short_time_patterns,
-                       NUM_SHORT_TIME_PATTERNS));
+
+       MonoArray *long_time_patterns = create_names_array_idx_dynamic (dfe->long_time_patterns,
+                                                                       NUM_LONG_TIME_PATTERNS, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       MONO_OBJECT_SETREF (this_obj, LongTimePatterns, long_time_patterns);
+
+       MonoArray *short_time_patterns = create_names_array_idx_dynamic (dfe->short_time_patterns,
+                                                                        NUM_SHORT_TIME_PATTERNS, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       MONO_OBJECT_SETREF (this_obj, ShortTimePatterns, short_time_patterns);
        this_obj->FirstDayOfWeek = dfe->first_day_of_week;
        this_obj->CalendarWeekRule = dfe->calendar_week_rule;
 }
@@ -228,6 +276,7 @@ ves_icall_System_Globalization_CultureData_fill_culture_data (MonoCultureData *t
 void
 ves_icall_System_Globalization_CultureData_fill_number_data (MonoNumberFormatInfo* number, gint32 number_index)
 {
+       MonoError error;
        MonoDomain *domain;
        const NumberFormatEntry *nfe;
 
@@ -242,8 +291,11 @@ ves_icall_System_Globalization_CultureData_fill_number_data (MonoNumberFormatInf
                        idx2string (nfe->currency_decimal_separator)));
        MONO_OBJECT_SETREF (number, currencyGroupSeparator, mono_string_new (domain,
                        idx2string (nfe->currency_group_separator)));
-       MONO_OBJECT_SETREF (number, currencyGroupSizes, create_group_sizes_array (nfe->currency_group_sizes,
-                       GROUP_SIZE));
+       MonoArray *currency_sizes_arr = create_group_sizes_array (nfe->currency_group_sizes,
+                                                                 GROUP_SIZE, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       MONO_OBJECT_SETREF (number, currencyGroupSizes, currency_sizes_arr);
        number->currencyNegativePattern = nfe->currency_negative_pattern;
        number->currencyPositivePattern = nfe->currency_positive_pattern;
        MONO_OBJECT_SETREF (number, currencySymbol, mono_string_new (domain, idx2string (nfe->currency_symbol)));
@@ -255,8 +307,11 @@ ves_icall_System_Globalization_CultureData_fill_number_data (MonoNumberFormatInf
        MONO_OBJECT_SETREF (number, numberDecimalSeparator, mono_string_new (domain,
                        idx2string (nfe->number_decimal_separator)));
        MONO_OBJECT_SETREF (number, numberGroupSeparator, mono_string_new (domain, idx2string (nfe->number_group_separator)));
-       MONO_OBJECT_SETREF (number, numberGroupSizes, create_group_sizes_array (nfe->number_group_sizes,
-                       GROUP_SIZE));
+       MonoArray *number_sizes_arr = create_group_sizes_array (nfe->number_group_sizes,
+                                                               GROUP_SIZE, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+       MONO_OBJECT_SETREF (number, numberGroupSizes, number_sizes_arr);
        number->numberNegativePattern = nfe->number_negative_pattern;
        number->percentNegativePattern = nfe->percent_negative_pattern;
        number->percentPositivePattern = nfe->percent_positive_pattern;
@@ -268,10 +323,12 @@ ves_icall_System_Globalization_CultureData_fill_number_data (MonoNumberFormatInf
 }
 
 static MonoBoolean
-construct_culture (MonoCultureInfo *this_obj, const CultureInfoEntry *ci)
+construct_culture (MonoCultureInfo *this_obj, const CultureInfoEntry *ci, MonoError *error)
 {
        MonoDomain *domain = mono_domain_get ();
 
+       mono_error_init (error);
+
        this_obj->lcid = ci->lcid;
        MONO_OBJECT_SETREF (this_obj, name, mono_string_new (domain, idx2string (ci->name)));
        MONO_OBJECT_SETREF (this_obj, englishname, mono_string_new (domain, idx2string (ci->englishname)));
@@ -283,7 +340,10 @@ construct_culture (MonoCultureInfo *this_obj, const CultureInfoEntry *ci)
        // It's null for neutral cultures
        if (ci->territory > 0)
                MONO_OBJECT_SETREF (this_obj, territory, mono_string_new (domain, idx2string (ci->territory)));
-       MONO_OBJECT_SETREF (this_obj, native_calendar_names, create_names_array_idx (ci->native_calendar_names, NUM_CALENDARS));
+
+       MonoArray *native_calendar_names = create_names_array_idx (ci->native_calendar_names, NUM_CALENDARS, error);
+       return_val_if_nok (error, FALSE);
+       MONO_OBJECT_SETREF (this_obj, native_calendar_names, native_calendar_names);
        this_obj->parent_lcid = ci->parent_lcid;
        this_obj->datetime_index = ci->datetime_format_index;
        this_obj->number_index = ci->number_format_index;
@@ -492,19 +552,25 @@ MonoBoolean
 ves_icall_System_Globalization_CultureInfo_construct_internal_locale_from_lcid (MonoCultureInfo *this_obj,
                gint lcid)
 {
+       MonoError error;
        const CultureInfoEntry *ci;
        
        ci = culture_info_entry_from_lcid (lcid);
        if(ci == NULL)
                return FALSE;
 
-       return construct_culture (this_obj, ci);
+       if (!construct_culture (this_obj, ci, &error)) {
+               mono_error_set_pending_exception (&error);
+               return FALSE;
+       }
+       return TRUE;
 }
 
 MonoBoolean
 ves_icall_System_Globalization_CultureInfo_construct_internal_locale_from_name (MonoCultureInfo *this_obj,
                MonoString *name)
 {
+       MonoError error;
        const CultureInfoNameEntry *ne;
        char *n;
        
@@ -519,7 +585,11 @@ ves_icall_System_Globalization_CultureInfo_construct_internal_locale_from_name (
        }
        g_free (n);
 
-       return construct_culture (this_obj, &culture_entries [ne->culture_entry_index]);
+       if (!construct_culture (this_obj, &culture_entries [ne->culture_entry_index], &error)) {
+               mono_error_set_pending_exception (&error);
+               return FALSE;
+       }
+       return TRUE;
 }
 /*
 MonoBoolean
@@ -600,7 +670,9 @@ ves_icall_System_Globalization_CultureInfo_internal_get_cultures (MonoBoolean ne
        if (neutral)
                len++;
 
-       ret = mono_array_new (domain, klass, len);
+       ret = mono_array_new_checked (domain, klass, len, &error);
+       if (!is_ok (&error))
+               goto fail;
 
        if (len == 0)
                return ret;
@@ -617,7 +689,8 @@ ves_icall_System_Globalization_CultureInfo_internal_get_cultures (MonoBoolean ne
                        if (!is_ok (&error)) goto fail;
                        mono_runtime_object_init_checked ((MonoObject *) culture, &error);
                        if (!is_ok (&error)) goto fail;
-                       construct_culture (culture, ci);
+                       if (!construct_culture (culture, ci, &error))
+                               goto fail;
                        culture->use_user_override = TRUE;
                        mono_array_setref (ret, len++, culture);
                }
@@ -641,13 +714,17 @@ int ves_icall_System_Globalization_CompareInfo_internal_compare (MonoCompareInfo
 
 void ves_icall_System_Globalization_CompareInfo_assign_sortkey (MonoCompareInfo *this_obj, MonoSortKey *key, MonoString *source, gint32 options)
 {
+       MonoError error;
        MonoArray *arr;
        gint32 keylen, i;
 
        keylen=mono_string_length (source);
        
-       arr=mono_array_new (mono_domain_get (), mono_get_byte_class (),
-                           keylen);
+       arr=mono_array_new_checked (mono_domain_get (), mono_get_byte_class (),
+                                   keylen, &error);
+       if (mono_error_set_pending_exception (&error))
+               return;
+
        for(i=0; i<keylen; i++) {
                mono_array_set (arr, guint8, i, mono_string_chars (source)[i]);
        }
index 696b97deca31c7385e56335cb44f4c2af65aa062..13ef2b4c486a68e9b8ca8be2303d851b22aebcf2 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -211,11 +212,11 @@ init_safe_handle ()
 }
 
 static void
-register_icall (gpointer func, const char *name, const char *sigstr, gboolean save)
+register_icall (gpointer func, const char *name, const char *sigstr, gboolean no_wrapper)
 {
        MonoMethodSignature *sig = mono_create_icall_signature (sigstr);
 
-       mono_register_jit_icall (func, name, sig, save);
+       mono_register_jit_icall (func, name, sig, no_wrapper);
 }
 
 MonoMethodSignature*
@@ -237,6 +238,15 @@ mono_marshal_init_tls (void)
        mono_native_tls_alloc (&load_type_info_tls_id, NULL);
 }
 
+static MonoObject*
+mono_object_isinst_icall (MonoObject *obj, MonoClass *klass)
+{
+       MonoError error;
+       MonoObject *result = mono_object_isinst_checked (obj, klass, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
 void
 mono_marshal_init (void)
 {
@@ -284,7 +294,7 @@ mono_marshal_init (void)
                register_icall (mono_string_to_byvalstr, "mono_string_to_byvalstr", "void ptr ptr int32", FALSE);
                register_icall (mono_string_to_byvalwstr, "mono_string_to_byvalwstr", "void ptr ptr int32", FALSE);
                register_icall (g_free, "g_free", "void ptr", FALSE);
-               register_icall (mono_object_isinst, "mono_object_isinst", "object object ptr", FALSE);
+               register_icall (mono_object_isinst_icall, "mono_object_isinst_icall", "object object ptr", FALSE);
                register_icall (mono_struct_delete_old, "mono_struct_delete_old", "void ptr ptr", FALSE);
                register_icall (mono_delegate_begin_invoke, "mono_delegate_begin_invoke", "object object ptr", FALSE);
                register_icall (mono_delegate_end_invoke, "mono_delegate_end_invoke", "object object ptr", FALSE);
@@ -352,7 +362,7 @@ mono_delegate_to_ftnptr (MonoDelegate *delegate)
        if (delegate->method_is_virtual)
                method = mono_object_get_virtual_method (delegate->target, method);
 
-       if (mono_method_signature (method)->pinvoke) {
+       if (method->flags & METHOD_ATTRIBUTE_PINVOKE_IMPL) {
                const char *exc_class, *exc_arg;
                gpointer ftnptr;
 
@@ -519,7 +529,11 @@ mono_ftnptr_to_delegate (MonoClass *klass, gpointer ftn)
 
                if (use_aot_wrappers) {
                        wrapper = mono_marshal_get_native_func_wrapper_aot (klass);
-                       this_obj = mono_value_box (mono_domain_get (), mono_defaults.int_class, &ftn);
+                       this_obj = mono_value_box_checked (mono_domain_get (), mono_defaults.int_class, &ftn, &error);
+                       if (!is_ok (&error)) {
+                               mono_error_set_pending_exception (&error);
+                               return NULL;
+                       }
                } else {
                        memset (&piinfo, 0, sizeof (piinfo));
                        parse_unmanaged_function_pointer_attr (klass, &piinfo);
@@ -592,9 +606,11 @@ mono_delegate_free_ftnptr (MonoDelegate *delegate)
        }
 }
 
+/* This is a JIT icall, it sets the pending exception and returns NULL on error */
 static MonoString *
 mono_string_from_byvalstr (const char *data, int max_len)
 {
+       MonoError error;
        MonoDomain *domain = mono_domain_get ();
        int len = 0;
 
@@ -604,7 +620,9 @@ mono_string_from_byvalstr (const char *data, int max_len)
        while (len < max_len - 1 && data [len])
                len++;
 
-       return mono_string_new_len (domain, data, len);
+       MonoString *result = mono_string_new_len_checked (domain, data, len, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 /* This is a JIT icall, it sets the pending exception and return NULL on error */
@@ -1112,10 +1130,14 @@ mono_string_to_byvalwstr (gpointer dst, MonoString *src, int size)
        *((gunichar2 *) dst + len) = 0;
 }
 
+/* this is an icall, it sets the pending exception and returns NULL on error */
 static MonoString*
 mono_string_new_len_wrapper (const char *text, guint length)
 {
-       return mono_string_new_len (mono_domain_get (), text, length);
+       MonoError error;
+       MonoString *result = mono_string_new_len_checked (mono_domain_get (), text, length, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 #ifndef DISABLE_JIT
@@ -1202,7 +1224,8 @@ guint
 mono_type_to_stind (MonoType *type)
 {
        if (type->byref)
-               return CEE_STIND_I;
+               return MONO_TYPE_IS_REFERENCE (type) ? CEE_STIND_REF : CEE_STIND_I;
+
 
 handle_enum:
        switch (type->type) {
@@ -1298,7 +1321,7 @@ emit_ptr_to_object_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
                mono_mb_emit_ldloc (mb, 1);
                mono_mb_emit_icon (mb, mspec->data.array_data.num_elem);
                mono_mb_emit_op (mb, CEE_NEWARR, eklass);       
-               mono_mb_emit_byte (mb, CEE_STIND_I);
+               mono_mb_emit_byte (mb, CEE_STIND_REF);
 
                if (eklass->blittable) {
                        /* copy the elements */
@@ -1536,16 +1559,23 @@ emit_ptr_to_object_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
 }
 
 static gpointer
-conv_to_icall (MonoMarshalConv conv)
+conv_to_icall (MonoMarshalConv conv, int *ind_store_type)
 {
+       int dummy;
+       if (!ind_store_type)
+               ind_store_type = &dummy;
+       *ind_store_type = CEE_STIND_I;
        switch (conv) {
        case MONO_MARSHAL_CONV_STR_LPWSTR:
                return mono_marshal_string_to_utf16;            
        case MONO_MARSHAL_CONV_LPWSTR_STR:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_from_utf16;
        case MONO_MARSHAL_CONV_LPTSTR_STR:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_new_wrapper;
        case MONO_MARSHAL_CONV_LPSTR_STR:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_new_wrapper;
        case MONO_MARSHAL_CONV_STR_LPTSTR:
 #ifdef TARGET_WIN32
@@ -1558,6 +1588,7 @@ conv_to_icall (MonoMarshalConv conv)
        case MONO_MARSHAL_CONV_STR_BSTR:
                return mono_string_to_bstr;
        case MONO_MARSHAL_CONV_BSTR_STR:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_from_bstr;
        case MONO_MARSHAL_CONV_STR_TBSTR:
        case MONO_MARSHAL_CONV_STR_ANSIBSTR:
@@ -1581,16 +1612,20 @@ conv_to_icall (MonoMarshalConv conv)
        case MONO_MARSHAL_CONV_DEL_FTN:
                return mono_delegate_to_ftnptr;
        case MONO_MARSHAL_CONV_FTN_DEL:
+               *ind_store_type = CEE_STIND_REF;
                return mono_ftnptr_to_delegate;
        case MONO_MARSHAL_CONV_LPSTR_SB:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_utf8_to_builder;
        case MONO_MARSHAL_CONV_LPTSTR_SB:
+               *ind_store_type = CEE_STIND_REF;
 #ifdef TARGET_WIN32
                return mono_string_utf16_to_builder;
 #else
                return mono_string_utf8_to_builder;
 #endif
        case MONO_MARSHAL_CONV_LPWSTR_SB:
+               *ind_store_type = CEE_STIND_REF;
                return mono_string_utf16_to_builder;
        case MONO_MARSHAL_FREE_ARRAY:
                return mono_marshal_free_array;
@@ -1609,6 +1644,7 @@ static void
 emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv conv, MonoMarshalSpec *mspec)
 {
        int pos;
+       int stind_op;
 
        switch (conv) {
        case MONO_MARSHAL_CONV_BOOL_I4:
@@ -1643,8 +1679,8 @@ emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
                mono_mb_emit_ldloc (mb, 1);
                mono_mb_emit_ldloc (mb, 0);
                mono_mb_emit_byte (mb, CEE_LDIND_REF);
-               mono_mb_emit_icall (mb, conv_to_icall (conv));
-               mono_mb_emit_byte (mb, CEE_STIND_I);    
+               mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+               mono_mb_emit_byte (mb, stind_op);
                break;
        }
        case MONO_MARSHAL_CONV_ARRAY_SAVEARRAY:
@@ -1653,8 +1689,8 @@ emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
                mono_mb_emit_ldloc (mb, 1);
                mono_mb_emit_ldloc (mb, 0);
                mono_mb_emit_byte (mb, CEE_LDIND_REF);
-               mono_mb_emit_icall (mb, conv_to_icall (conv));
-               mono_mb_emit_byte (mb, CEE_STIND_I);    
+               mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+               mono_mb_emit_byte (mb, stind_op);
                break;
        case MONO_MARSHAL_CONV_STR_BYVALSTR: 
        case MONO_MARSHAL_CONV_STR_BYVALWSTR: {
@@ -1664,7 +1700,7 @@ emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
                mono_mb_emit_ldloc (mb, 0);     
                mono_mb_emit_byte (mb, CEE_LDIND_REF); /* src String */
                mono_mb_emit_icon (mb, mspec->data.array_data.num_elem);
-               mono_mb_emit_icall (mb, conv_to_icall (conv));
+               mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                break;
        }
        case MONO_MARSHAL_CONV_ARRAY_BYVALARRAY: {
@@ -1843,11 +1879,7 @@ emit_object_to_ptr_conv (MonoMethodBuilder *mb, MonoType *type, MonoMarshalConv
        }
                
        default: {
-               char *msg = g_strdup_printf ("marshalling conversion %d not implemented", conv);
-               MonoException *exc = mono_get_exception_not_implemented (msg);
-               g_warning ("%s", msg);
-               g_free (msg);
-               mono_raise_exception (exc);
+               g_error ("marshalling conversion %d not implemented", conv);
        }
        }
 }
@@ -1930,8 +1962,9 @@ emit_struct_conv_full (MonoMethodBuilder *mb, MonoClass *klass, gboolean to_obje
                case MONO_MARSHAL_CONV_NONE: {
                        int t;
 
-                       if (ftype->byref || ftype->type == MONO_TYPE_I ||
-                           ftype->type == MONO_TYPE_U) {
+                       //XXX a byref field!?!? that's not allowed! and worse, it might miss a WB
+                       g_assert (!ftype->byref);
+                       if (ftype->type == MONO_TYPE_I || ftype->type == MONO_TYPE_U) {
                                mono_mb_emit_ldloc (mb, 1);
                                mono_mb_emit_ldloc (mb, 0);
                                mono_mb_emit_byte (mb, CEE_LDIND_I);
@@ -2205,7 +2238,9 @@ mono_delegate_begin_invoke (MonoDelegate *delegate, gpointer *params)
                method = mono_get_delegate_invoke (klass);
        g_assert (method);
 
-       return mono_threadpool_ms_begin_invoke (mono_domain_get (), (MonoObject*) delegate, method, params);
+       MonoAsyncResult *result = mono_threadpool_ms_begin_invoke (mono_domain_get (), (MonoObject*) delegate, method, params, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 #ifndef DISABLE_JIT
@@ -2334,7 +2369,7 @@ mono_marshal_get_string_to_ptr_conv (MonoMethodPInvoke *piinfo, MonoMarshalSpec
        case MONO_NATIVE_BSTR:
                return MONO_MARSHAL_CONV_STR_BSTR;
        default:
-               return (MonoMarshalConv)-1;
+               return MONO_MARSHAL_CONV_INVALID;
        }
 }
 
@@ -2354,7 +2389,7 @@ mono_marshal_get_stringbuilder_to_ptr_conv (MonoMethodPInvoke *piinfo, MonoMarsh
                return MONO_MARSHAL_CONV_SB_LPTSTR;
                break;
        default:
-               return (MonoMarshalConv)-1;
+               return MONO_MARSHAL_CONV_INVALID;
        }
 }
 
@@ -2377,7 +2412,7 @@ mono_marshal_get_ptr_to_string_conv (MonoMethodPInvoke *piinfo, MonoMarshalSpec
        case MONO_NATIVE_BSTR:
                return MONO_MARSHAL_CONV_BSTR_STR;
        default:
-               return (MonoMarshalConv)-1;
+               return MONO_MARSHAL_CONV_INVALID;
        }
 }
 
@@ -2403,7 +2438,7 @@ mono_marshal_get_ptr_to_stringbuilder_conv (MonoMethodPInvoke *piinfo, MonoMarsh
                return MONO_MARSHAL_CONV_LPTSTR_SB;
                break;
        default:
-               return (MonoMarshalConv)-1;
+               return MONO_MARSHAL_CONV_INVALID;
        }
 }
 
@@ -2952,7 +2987,8 @@ mono_delegate_end_invoke (MonoDelegate *delegate, gpointer *params)
                mono_set_pending_exception ((MonoException*)exc);
        }
 
-       mono_method_return_message_restore (method, params, out_args);
+       mono_method_return_message_restore (method, params, out_args, &error);
+       mono_error_set_pending_exception (&error);
        return res;
 }
 
@@ -5093,11 +5129,11 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_ldarg (mb, argnum);
                }
 
-               if (conv == -1) {
+               if (conv == MONO_MARSHAL_CONV_INVALID) {
                        char *msg = g_strdup_printf ("string marshalling conversion %d not implemented", encoding);
                        mono_mb_emit_exception_marshal_directive (mb, msg);
                } else {
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
 
                        mono_mb_emit_stloc (mb, conv_arg);
                }
@@ -5105,7 +5141,7 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
 
        case MARSHAL_ACTION_CONV_OUT:
                conv = mono_marshal_get_ptr_to_string_conv (m->piinfo, spec, &need_free);
-               if (conv == -1) {
+               if (conv == MONO_MARSHAL_CONV_INVALID) {
                        char *msg = g_strdup_printf ("string marshalling conversion %d not implemented", encoding);
                        mono_mb_emit_exception_marshal_directive (mb, msg);
                        break;
@@ -5138,10 +5174,11 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_icall (mb, mono_string_new_len_wrapper);
                        mono_mb_emit_byte (mb, CEE_STIND_REF);
                } else if (t->byref && (t->attrs & PARAM_ATTRIBUTE_OUT || !(t->attrs & PARAM_ATTRIBUTE_IN))) {
+                       int stind_op;
                        mono_mb_emit_ldarg (mb, argnum);
                        mono_mb_emit_ldloc (mb, conv_arg);
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
-                       mono_mb_emit_byte (mb, CEE_STIND_REF);
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+                       mono_mb_emit_byte (mb, stind_op);
                        need_free = TRUE;
                }
 
@@ -5165,14 +5202,14 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
                mono_mb_emit_stloc (mb, 0);
                                
                conv = mono_marshal_get_ptr_to_string_conv (m->piinfo, spec, &need_free);
-               if (conv == -1) {
+               if (conv == MONO_MARSHAL_CONV_INVALID) {
                        char *msg = g_strdup_printf ("string marshalling conversion %d not implemented", encoding);
                        mono_mb_emit_exception_marshal_directive (mb, msg);
                        break;
                }
 
                mono_mb_emit_ldloc (mb, 0);
-               mono_mb_emit_icall (mb, conv_to_icall (conv));
+               mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                mono_mb_emit_stloc (mb, 3);
 
                /* free the string */
@@ -5194,7 +5231,7 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
                }
 
                conv = mono_marshal_get_ptr_to_string_conv (m->piinfo, spec, &need_free);
-               if (conv == -1) {
+               if (conv == MONO_MARSHAL_CONV_INVALID) {
                        char *msg = g_strdup_printf ("string marshalling conversion %d not implemented", encoding);
                        mono_mb_emit_exception_marshal_directive (mb, msg);
                        break;
@@ -5203,27 +5240,28 @@ emit_marshal_string (EmitMarshalContext *m, int argnum, MonoType *t,
                mono_mb_emit_ldarg (mb, argnum);
                if (t->byref)
                        mono_mb_emit_byte (mb, CEE_LDIND_I);
-               mono_mb_emit_icall (mb, conv_to_icall (conv));
+               mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                mono_mb_emit_stloc (mb, conv_arg);
                break;
 
        case MARSHAL_ACTION_MANAGED_CONV_OUT:
                if (t->byref) {
                        if (conv_arg) {
+                               int stind_op;
                                mono_mb_emit_ldarg (mb, argnum);
                                mono_mb_emit_ldloc (mb, conv_arg);
-                               mono_mb_emit_icall (mb, conv_to_icall (conv));
-                               mono_mb_emit_byte (mb, CEE_STIND_I);
+                               mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+                               mono_mb_emit_byte (mb, stind_op);
                        }
                }
                break;
 
        case MARSHAL_ACTION_MANAGED_CONV_RESULT:
-               if (conv_to_icall (conv) == mono_marshal_string_to_utf16)
+               if (conv_to_icall (conv, NULL) == mono_marshal_string_to_utf16)
                        /* We need to make a copy so the caller is able to free it */
                        mono_mb_emit_icall (mb, mono_marshal_string_to_utf16_copy);
                else
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                mono_mb_emit_stloc (mb, 3);
                break;
 
@@ -5502,7 +5540,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                                mono_mb_emit_stloc (mb, conv_arg);
                        } else {
                                mono_mb_emit_ldarg (mb, argnum);
-                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN));
+                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN, NULL));
                                mono_mb_emit_stloc (mb, conv_arg);
                        }
                } else if (klass == mono_defaults.stringbuilder_class) {
@@ -5522,7 +5560,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                        if (t->byref && !(t->attrs & PARAM_ATTRIBUTE_IN) && (t->attrs & PARAM_ATTRIBUTE_OUT))
                                break;
 
-                       if (conv == -1) {
+                       if (conv == MONO_MARSHAL_CONV_INVALID) {
                                char *msg = g_strdup_printf ("stringbuilder marshalling conversion %d not implemented", encoding);
                                mono_mb_emit_exception_marshal_directive (mb, msg);
                                break;
@@ -5532,7 +5570,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                        if (t->byref)
                                mono_mb_emit_byte (mb, CEE_LDIND_I);
 
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                        mono_mb_emit_stloc (mb, conv_arg);
                } else if (klass->blittable) {
                        mono_mb_emit_byte (mb, CEE_LDNULL);
@@ -5634,7 +5672,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                                mono_mb_emit_ldarg (mb, argnum);
                                mono_mb_emit_ldloc (mb, conv_arg);
 
-                               mono_mb_emit_icall (mb, conv_to_icall (conv));
+                               mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                        }
 
                        if (need_free) {
@@ -5650,7 +5688,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                                mono_mb_emit_byte (mb, MONO_CUSTOM_PREFIX);
                                mono_mb_emit_op (mb, CEE_MONO_CLASSCONST, klass);
                                mono_mb_emit_ldloc (mb, conv_arg);
-                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL));
+                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL, NULL));
                                mono_mb_emit_byte (mb, CEE_STIND_REF);
                        }
                        break;
@@ -5733,7 +5771,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_byte (mb, MONO_CUSTOM_PREFIX);
                        mono_mb_emit_op (mb, CEE_MONO_CLASSCONST, klass);
                        mono_mb_emit_ldloc (mb, 0);
-                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL));
+                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL, NULL));
                        mono_mb_emit_stloc (mb, 3);
                } else {
                        /* set src */
@@ -5783,7 +5821,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_ldarg (mb, argnum);
                        if (t->byref)
                                mono_mb_emit_byte (mb, CEE_LDIND_I);
-                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL));
+                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_FTN_DEL, NULL));
                        mono_mb_emit_stloc (mb, conv_arg);
                        break;
                }
@@ -5857,10 +5895,11 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
        case MARSHAL_ACTION_MANAGED_CONV_OUT:
                if (klass->delegate) {
                        if (t->byref) {
+                               int stind_op;
                                mono_mb_emit_ldarg (mb, argnum);
                                mono_mb_emit_ldloc (mb, conv_arg);
-                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN));
-                               mono_mb_emit_byte (mb, CEE_STIND_I);
+                               mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN, &stind_op));
+                               mono_mb_emit_byte (mb, stind_op);
                                break;
                        }
                }
@@ -5919,7 +5958,7 @@ emit_marshal_object (EmitMarshalContext *m, int argnum, MonoType *t,
 
        case MARSHAL_ACTION_MANAGED_CONV_RESULT:
                if (klass->delegate) {
-                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN));
+                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_DEL_FTN, NULL));
                        mono_mb_emit_stloc (mb, 3);
                        break;
                }
@@ -6136,7 +6175,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_ldarg (mb, argnum);
                        if (t->byref)
                                mono_mb_emit_byte (mb, CEE_LDIND_I);
-                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_ARRAY_LPARRAY));
+                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_CONV_ARRAY_LPARRAY, NULL));
                        mono_mb_emit_stloc (mb, conv_arg);
                } else {
                        MonoClass *eklass;
@@ -6158,9 +6197,9 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                                conv = mono_marshal_get_stringbuilder_to_ptr_conv (m->piinfo, spec);
                        }
                        else
-                               conv = (MonoMarshalConv)-1;
+                               conv = MONO_MARSHAL_CONV_INVALID;
 
-                       if (is_string && conv == -1) {
+                       if (is_string && conv == MONO_MARSHAL_CONV_INVALID) {
                                char *msg = g_strdup_printf ("string/stringbuilder marshalling conversion %d not implemented", encoding);
                                mono_mb_emit_exception_marshal_directive (mb, msg);
                                break;
@@ -6216,12 +6255,13 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        /* Emit marshalling code */
 
                        if (is_string) {
+                               int stind_op;
                                mono_mb_emit_ldloc (mb, dest_ptr);
                                mono_mb_emit_ldloc (mb, src_var);
                                mono_mb_emit_ldloc (mb, index_var);
                                mono_mb_emit_byte (mb, CEE_LDELEM_REF);
-                               mono_mb_emit_icall (mb, conv_to_icall (conv));
-                               mono_mb_emit_byte (mb, CEE_STIND_I);
+                               mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+                               mono_mb_emit_byte (mb, stind_op);
                        } else {
                                /* set the src_ptr */
                                mono_mb_emit_ldloc (mb, src_var);
@@ -6285,7 +6325,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                                mono_mb_emit_byte (mb, CEE_CONV_OVF_I);
                                mono_mb_emit_op (mb, CEE_NEWARR, klass->element_class);
                                /* Store into argument */
-                               mono_mb_emit_byte (mb, CEE_STIND_I);
+                               mono_mb_emit_byte (mb, CEE_STIND_REF);
                        }
                }
 
@@ -6332,7 +6372,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                                gboolean need_free2;
                                MonoMarshalConv conv = mono_marshal_get_ptr_to_stringbuilder_conv (m->piinfo, spec, &need_free2);
 
-                               g_assert (conv != -1);
+                               g_assert (conv != MONO_MARSHAL_CONV_INVALID);
 
                                /* dest */
                                mono_mb_emit_ldarg (mb, argnum);
@@ -6345,7 +6385,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                                mono_mb_emit_ldloc (mb, src_ptr);
                                mono_mb_emit_byte (mb, CEE_LDIND_I);
 
-                               mono_mb_emit_icall (mb, conv_to_icall (conv));
+                               mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
 
                                if (need_free) {
                                        /* src */
@@ -6407,7 +6447,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        if (t->byref)
                                mono_mb_emit_byte (mb, CEE_LDIND_REF);
                        mono_mb_emit_ldloc (mb, conv_arg);
-                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_FREE_LPARRAY));
+                       mono_mb_emit_icall (mb, conv_to_icall (MONO_MARSHAL_FREE_LPARRAY, NULL));
                }
 
                break;
@@ -6479,7 +6519,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        conv = mono_marshal_get_ptr_to_stringbuilder_conv (m->piinfo, spec, &need_free);
                }
                else
-                       conv = (MonoMarshalConv)-1;
+                       conv = MONO_MARSHAL_CONV_INVALID;
 
                mono_marshal_load_type_info (eklass);
 
@@ -6574,7 +6614,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
 
                /* Emit marshalling code */
                if (is_string) {
-                       g_assert (conv != -1);
+                       g_assert (conv != MONO_MARSHAL_CONV_INVALID);
 
                        mono_mb_emit_ldloc (mb, conv_arg);
                        mono_mb_emit_ldloc (mb, index_var);
@@ -6582,7 +6622,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        mono_mb_emit_ldloc (mb, src_ptr);
                        mono_mb_emit_byte (mb, CEE_LDIND_I);
 
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, NULL));
                        mono_mb_emit_byte (mb, CEE_STELEM_REF);
                }
                else {
@@ -6642,7 +6682,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                        conv = mono_marshal_get_stringbuilder_to_ptr_conv (m->piinfo, spec);
                }
                else
-                       conv = (MonoMarshalConv)-1;
+                       conv = MONO_MARSHAL_CONV_INVALID;
 
                mono_marshal_load_type_info (eklass);
 
@@ -6690,7 +6730,8 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
 
                /* Emit marshalling code */
                if (is_string) {
-                       g_assert (conv != -1);
+                       int stind_op;
+                       g_assert (conv != MONO_MARSHAL_CONV_INVALID);
 
                        /* dest */
                        mono_mb_emit_ldloc (mb, dest_ptr);
@@ -6701,8 +6742,8 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
 
                        mono_mb_emit_byte (mb, CEE_LDELEM_REF);
 
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
-                       mono_mb_emit_byte (mb, CEE_STIND_I);
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+                       mono_mb_emit_byte (mb, stind_op);
                }
                else {
                        char *msg = g_strdup ("Marshalling of non-string and non-blittable arrays to managed code is not implemented.");
@@ -6724,7 +6765,7 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
                MonoClass *eklass;
                guint32 label1, label2, label3;
                int index_var, src, dest, esize;
-               MonoMarshalConv conv = (MonoMarshalConv)-1;
+               MonoMarshalConv conv = MONO_MARSHAL_CONV_INVALID;
                gboolean is_string = FALSE;
                
                g_assert (!t->byref);
@@ -6787,7 +6828,8 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
 
                /* Emit marshalling code */
                if (is_string) {
-                       g_assert (conv != -1);
+                       int stind_op;
+                       g_assert (conv != MONO_MARSHAL_CONV_INVALID);
 
                        /* dest */
                        mono_mb_emit_ldloc (mb, dest);
@@ -6798,8 +6840,8 @@ emit_marshal_array (EmitMarshalContext *m, int argnum, MonoType *t,
 
                        mono_mb_emit_byte (mb, CEE_LDELEM_REF);
 
-                       mono_mb_emit_icall (mb, conv_to_icall (conv));
-                       mono_mb_emit_byte (mb, CEE_STIND_I);
+                       mono_mb_emit_icall (mb, conv_to_icall (conv, &stind_op));
+                       mono_mb_emit_byte (mb, stind_op);
                }
                else {
                        char *msg = g_strdup ("Marshalling of non-string arrays to managed code is not implemented.");
@@ -7151,10 +7193,12 @@ emit_marshal (EmitMarshalContext *m, int argnum, MonoType *t,
                return emit_marshal_string (m, argnum, t, spec, conv_arg, conv_arg_type, action);
        case MONO_TYPE_CLASS:
        case MONO_TYPE_OBJECT:
-#ifndef DISABLE_COM
+#if !defined(DISABLE_COM) && !defined(DISABLE_JIT)
                if (spec && spec->native == MONO_NATIVE_STRUCT)
                        return emit_marshal_variant (m, argnum, t, spec, conv_arg, conv_arg_type, action);
+#endif
 
+#if !defined(DISABLE_COM)
                if (spec && (spec->native == MONO_NATIVE_IUNKNOWN ||
                        spec->native == MONO_NATIVE_IDISPATCH ||
                        spec->native == MONO_NATIVE_INTERFACE))
@@ -8226,7 +8270,7 @@ mono_marshal_get_managed_wrapper (MonoMethod *method, MonoClass *delegate_klass,
        EmitMarshalContext m;
 
        g_assert (method != NULL);
-       g_assert (!mono_method_signature (method)->pinvoke);
+       g_assert (!(method->flags & METHOD_ATTRIBUTE_PINVOKE_IMPL));
 
        /* 
         * FIXME: Should cache the method+delegate type pair, since the same method
@@ -8587,7 +8631,9 @@ mono_marshal_get_castclass_with_cache (void)
 static MonoObject *
 mono_marshal_isinst_with_cache (MonoObject *obj, MonoClass *klass, uintptr_t *cache)
 {
-       MonoObject *isinst = mono_object_isinst (obj, klass);
+       MonoError error;
+       MonoObject *isinst = mono_object_isinst_checked (obj, klass, &error);
+       mono_error_raise_exception (&error); /* FIXME don't raise here */
 
 #ifndef DISABLE_REMOTING
        if (obj->vtable->klass == mono_defaults.transparent_proxy_class)
@@ -8649,7 +8695,7 @@ mono_marshal_get_isinst_with_cache (void)
 
        // return obj
        mono_mb_patch_branch (mb, positive_cache_hit_pos);
-       mono_mb_emit_ldarg (mb, 0);
+       mono_mb_emit_ldarg (mb, obj_arg_position);
        mono_mb_emit_byte (mb, CEE_RET);
 #endif
 
@@ -9490,7 +9536,7 @@ get_virtual_stelemref_wrapper (int kind)
                /*if (mono_object_isinst (value, aklass)) */
                mono_mb_emit_ldarg (mb, 2);
                mono_mb_emit_ldloc (mb, aklass);
-               mono_mb_emit_icall (mb, mono_object_isinst);
+               mono_mb_emit_icall (mb, mono_object_isinst_icall);
                b2 = mono_mb_emit_branch (mb, CEE_BRFALSE);
 
                /* do_store: */
@@ -9604,7 +9650,7 @@ get_virtual_stelemref_wrapper (int kind)
                /*if (mono_object_isinst (value, aklass)) */
                mono_mb_emit_ldarg (mb, 2);
                mono_mb_emit_ldloc (mb, aklass);
-               mono_mb_emit_icall (mb, mono_object_isinst);
+               mono_mb_emit_icall (mb, mono_object_isinst_icall);
                b2 = mono_mb_emit_branch (mb, CEE_BRFALSE);
 
                /* if (vklass->idepth < aklass->idepth) goto failue */
@@ -9930,7 +9976,7 @@ mono_marshal_get_stelemref (void)
        
        mono_mb_emit_ldarg (mb, 2);
        mono_mb_emit_ldloc (mb, aklass);
-       mono_mb_emit_icall (mb, mono_object_isinst);
+       mono_mb_emit_icall (mb, mono_object_isinst_icall);
        
        b4 = mono_mb_emit_branch (mb, CEE_BRTRUE);
        mono_mb_patch_addr (mb, b4, copy_pos - (b4 + 4));
@@ -10469,12 +10515,15 @@ ves_icall_System_Runtime_InteropServices_Marshal_PtrToStringAnsi (char *ptr)
 MonoString *
 ves_icall_System_Runtime_InteropServices_Marshal_PtrToStringAnsi_len (char *ptr, gint32 len)
 {
-       if (ptr == NULL) {
-               mono_set_pending_exception (mono_get_exception_argument_null ("ptr"));
-               return NULL;
-       } else {
-               return mono_string_new_len (mono_domain_get (), ptr, len);
-       }
+       MonoError error;
+       MonoString *result = NULL;
+       mono_error_init (&error);
+       if (ptr == NULL)
+               mono_error_set_argument_null (&error, "ptr", "");
+       else
+               result = mono_string_new_len_checked (mono_domain_get (), ptr, len, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 MonoString *
index abbdbdbace3b167545217577638bccda303b010a..60d36ae2ad1765d76cbf450dbb8feb9b616bf479 100644 (file)
@@ -10,6 +10,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc. (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 595369140103af94a4b1bb62e68a69eb0252712e..90a4d332bd129c818bebd54cb74b4e90ddd481f6 100644 (file)
@@ -1,6 +1,137 @@
+#include <stdio.h>
+
 #include "config.h"
+#include <mono/metadata/abi-details.h>
+
+#include <mono/metadata/class-internals.h>
+#include <mono/metadata/object-internals.h>
+#include <mono/metadata/monitor.h>
+#ifdef HAVE_SGEN_GC
+#include <mono/sgen/sgen-gc.h>
+#endif
+
+static int
+dump_arch (void)
+{
+#if defined (TARGET_X86)
+       g_print ("#ifdef TARGET_X86\n");
+#elif defined (TARGET_AMD64)
+       g_print ("#ifdef TARGET_AMD64\n");
+#elif defined (TARGET_ARM)
+       g_print ("#ifdef TARGET_ARM\n");
+#elif defined (TARGET_ARM64)
+       g_print ("#ifdef TARGET_ARM64\n");
+#else
+       return 0;
+#endif
+       return 1;
+}
+
+static int
+dump_os (void)
+{
+#if defined (PLATFORM_WIN32)
+       g_print ("#ifdef TARGET_WIN32\n");
+#elif defined (PLATFORM_ANDROID)
+       g_print ("#ifdef TARGET_ANDROID\n");
+#elif defined (PLATFORM_MACOSX)
+       g_print ("#ifdef TARGET_OSX\n");
+#elif defined (PLATFORM_IOS)
+       g_print ("#ifdef TARGET_IOS\n");
+#else
+       return 0;
+#endif
+       return 1;
+}
+
+void
+mono_dump_metadata_offsets (void);
+
+void
+mono_dump_metadata_offsets (void)
+{
+#ifdef USED_CROSS_COMPILER_OFFSETS
+       g_print ("not using native offsets\n");
+#else
+       g_print ("#ifndef USED_CROSS_COMPILER_OFFSETS\n");
+
+       if (!dump_arch ()) {
+               g_print ("#error failed to figure out the current arch\n");
+               return;
+       }
+
+       if (!dump_os ()) {
+               g_print ("#error failed to figure out the current OS\n");
+               return;
+       }
+
+#ifdef HAVE_SGEN_GC
+       g_print ("#ifndef HAVE_BOEHM_GC\n");
+#elif HAVE_BOEHM_GC
+       g_print ("#ifndef HAVE_SGEN_GC\n");
+#else
+       g_print ("#error no gc conf not supported\n");
+       return;
+#endif
+
+       g_print ("#define HAS_CROSS_COMPILER_OFFSETS\n");
+       g_print ("#if defined (USE_CROSS_COMPILE_OFFSETS) || defined (MONO_CROSS_COMPILE)\n");
+       g_print ("#if !defined (DISABLE_METADATA_OFFSETS)\n");
+       g_print ("#define USED_CROSS_COMPILER_OFFSETS\n");
+
+#define DISABLE_JIT_OFFSETS
+#define DECL_OFFSET2(struct,field,offset) this_should_not_happen
+#define DECL_ALIGN2(type,size) this_should_not_happen
+
+#define DECL_OFFSET(struct,field) g_print ("DECL_OFFSET2(%s,%s,%d)\n", #struct, #field, (int)MONO_STRUCT_OFFSET (struct, field));
+#define DECL_ALIGN(type) g_print ("DECL_ALIGN2(%s,%d)\n", #type, (int)MONO_ABI_ALIGNOF (type));
+#define DECL_SIZE(type) g_print ("DECL_SIZE2(%s,%d)\n", #type, (int)MONO_ABI_SIZEOF (type));
+#include <mono/metadata/object-offsets.h>
+
+       g_print ("#endif //disable metadata check\n");
+       g_print ("#endif //gc check\n");
+#endif
+}
+
+void
+mono_metadata_cross_helpers_run (void);
+
+void
+mono_metadata_cross_helpers_run (void)
+{
+#if defined (HAS_CROSS_COMPILER_OFFSETS) && !defined (MONO_CROSS_COMPILE)
+       gboolean is_broken = FALSE;
+
+#define DISABLE_JIT_OFFSETS
+#define USE_CROSS_COMPILE_OFFSETS
+#define DECL_OFFSET(struct,field) this_should_not_happen_for_cross_fields
+#define DECL_OFFSET2(struct,field,offset) \
+        if ((int)G_STRUCT_OFFSET (struct, field) != offset) { \
+               g_print (#struct ":" #field " invalid struct offset %d (expected %d)\n",        \
+                       offset, \
+                       (int)G_STRUCT_OFFSET (struct, field));  \
+               is_broken = TRUE;       \
+       }
+#define DECL_ALIGN(type) this_should_not_happen_for_cross_align
+#define DECL_ALIGN2(name,size) \
+        if (MONO_ALIGN_ ## name != size) { \
+               g_print (#name ": invalid alignment %d (expected %d)\n",        \
+               size,   \
+               MONO_ALIGN_ ## name);   \
+               is_broken = TRUE;       \
+       }
+#define DECL_SIZE(type) this_should_not_happen_for_cross_size
+#define DECL_SIZE2(name,size) \
+        if (MONO_SIZEOF_ ## name != size) { \
+               g_print (#name ": invalid size %d (expected %d)\n",     \
+               size,   \
+               MONO_SIZEOF_ ## name);  \
+               is_broken = TRUE;       \
+       }
+
+#include <mono/metadata/object-offsets.h>
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/metadata/metadata-cross-helpers.c"
+       g_assert (!is_broken);
 #endif
+}
 
index 57fc425083ef37f62392541ec68810018d0ebe15..6b8fdcb44ca396a788f220bac28c4795f2bd4752 100644 (file)
@@ -774,7 +774,7 @@ gboolean
 mono_metadata_generic_param_equal (MonoGenericParam *p1, MonoGenericParam *p2);
 
 void mono_dynamic_stream_reset  (MonoDynamicStream* stream);
-void mono_assembly_addref       (MonoAssembly *assembly);
+MONO_API void mono_assembly_addref       (MonoAssembly *assembly);
 void mono_assembly_load_friends (MonoAssembly* ass);
 gboolean mono_assembly_has_skip_verification (MonoAssembly* ass);
 
index 753e5269e921bdb9dec91aa0fdac4faf9f4f817b..287c68fbfb79d3413a3767ca63c0a9a0e3e66b35 100644 (file)
@@ -5,6 +5,7 @@
  *     Mono Project (http://www.mono-project.com)
  *
  * Copyright (C) 2005-2008 Novell, Inc. (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <mono/metadata/object-internals.h>
 #include <mono/metadata/verify.h>
index a96f8cee6380ae2adf0e67ff0d5f0c2cddf019ab..d278a7487ee68a8d59dce5902675362b2200dd39 100644 (file)
@@ -7,6 +7,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -1837,8 +1838,11 @@ mono_metadata_parse_signature (MonoImage *image, guint32 token)
        guint32 sig;
        const char *ptr;
 
-       if (image_is_dynamic (image))
-               return (MonoMethodSignature *)mono_lookup_dynamic_token (image, token, NULL);
+       if (image_is_dynamic (image)) {
+               ret = (MonoMethodSignature *)mono_lookup_dynamic_token (image, token, NULL, &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               return ret;
+       }
 
        g_assert (mono_metadata_token_table(token) == MONO_TABLE_STANDALONESIG);
                
@@ -2045,13 +2049,11 @@ mono_metadata_parse_method_signature_full (MonoImage *m, MonoGenericContainer *c
        for (i = 0; i < method->param_count; ++i) {
                if (*ptr == MONO_TYPE_SENTINEL) {
                        if (method->call_convention != MONO_CALL_VARARG || def) {
-                               mono_loader_assert_no_error ();
                                mono_error_set_bad_image (error, m, "Found sentinel for methoddef or no vararg");
                                g_free (pattrs);
                                return NULL;
                        }
                        if (method->sentinelpos >= 0) {
-                               mono_loader_assert_no_error ();
                                mono_error_set_bad_image (error, m, "Found sentinel twice in the same signature.");
                                g_free (pattrs);
                                return NULL;
@@ -2086,7 +2088,6 @@ mono_metadata_parse_method_signature_full (MonoImage *m, MonoGenericContainer *c
         * Add signature to a cache and increase ref count...
         */
 
-       mono_loader_assert_no_error ();
        return method;
 }
 
@@ -2766,24 +2767,11 @@ mono_metadata_clean_for_image (MonoImage *image)
 static void
 free_inflated_method (MonoMethodInflated *imethod)
 {
-       int i;
        MonoMethod *method = (MonoMethod*)imethod;
 
        if (method->signature)
                mono_metadata_free_inflated_signature (method->signature);
 
-       if (!((method->flags & METHOD_ATTRIBUTE_ABSTRACT) || (method->iflags & METHOD_IMPL_ATTRIBUTE_RUNTIME) || (method->iflags & METHOD_IMPL_ATTRIBUTE_INTERNAL_CALL) || (method->flags & METHOD_ATTRIBUTE_PINVOKE_IMPL))) {
-               MonoMethodHeader *header = imethod->header;
-
-               if (header) {
-                       /* Allocated in inflate_generic_header () */
-                       for (i = 0; i < header->num_locals; ++i)
-                               mono_metadata_free_type (header->locals [i]);
-                       g_free (header->clauses);
-                       g_free (header);
-               }
-       }
-
        g_free (method);
 }
 
@@ -3385,6 +3373,10 @@ do_mono_metadata_parse_type (MonoType *type, MonoImage *m, MonoGenericContainer
                        return FALSE;
 
                type->data.klass = mono_class_from_mono_type (etype);
+
+               if (transient)
+                       mono_metadata_free_type (etype);
+
                g_assert (type->data.klass); //This was previously a check for NULL, but mcfmt should never fail. It can return a borken MonoClass, but should return at least something.
                break;
        }
@@ -6168,7 +6160,6 @@ mono_metadata_load_generic_param_constraints_checked (MonoImage *image, guint32
                return TRUE;
        for (i = 0; i < container->type_argc; i++) {
                if (!get_constraints (image, start_row + i, &mono_generic_container_get_param_info (container, i)->constraints, container, error)) {
-                       mono_loader_assert_no_error ();
                        return FALSE;
                }
        }
index afc21d48e66a222e41b33846c4b5368659b977f0..35afec7e3eac6f0a4eea92c57f7aededa9b4c917 100644 (file)
 
 MONO_BEGIN_DECLS
 
-/*
- * When embedding, you have to define MONO_ZERO_LEN_ARRAY before including any
- * other Mono header file if you use a different compiler from the one used to
- * build Mono.
- */
-#ifndef MONO_ZERO_LEN_ARRAY
-#ifdef __GNUC__
-#define MONO_ZERO_LEN_ARRAY 0
-#else
-#define MONO_ZERO_LEN_ARRAY 1
-#endif
-#endif
-
 #define MONO_TYPE_ISSTRUCT(t) mono_type_is_struct (t)
 #define MONO_TYPE_IS_VOID(t) mono_type_is_void (t)
 #define MONO_TYPE_IS_POINTER(t) mono_type_is_pointer (t)
@@ -178,6 +165,8 @@ typedef enum {
        MONO_MARSHAL_CONV_HANDLEREF
 } MonoMarshalConv;
 
+#define MONO_MARSHAL_CONV_INVALID ((MonoMarshalConv)-1)
+
 typedef struct {
        MonoMarshalNative native;
        union {
index 3b04c246494af2d77121e5cbbb55fbade2bb2d3b..09e6027f4a0d53b7f5c2d50eed49cc7c59b1479b 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2002-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -97,6 +98,12 @@ void
 mono_mb_free (MonoMethodBuilder *mb)
 {
 #ifndef DISABLE_JIT
+       GList *l;
+
+       for (l = mb->locals_list; l; l = l->next) {
+               /* Allocated in mono_mb_add_local () */
+               g_free (l->data);
+       }
        g_list_free (mb->locals_list);
        if (!mb->dynamic) {
                g_free (mb->method);
@@ -149,7 +156,7 @@ mono_mb_create_method (MonoMethodBuilder *mb, MonoMethodSignature *signature, in
                header->code = mb->code;
 
                for (i = 0, l = mb->locals_list; l; l = l->next, i++) {
-                       header->locals [i] = mono_metadata_type_dup (NULL, (MonoType*)l->data);
+                       header->locals [i] = (MonoType*)l->data;
                }
        } else
 #endif
@@ -173,11 +180,17 @@ mono_mb_create_method (MonoMethodBuilder *mb, MonoMethodSignature *signature, in
                memcpy ((char*)header->code, mb->code, mb->pos);
 
                for (i = 0, l = mb->locals_list; l; l = l->next, i++) {
-                       header->locals [i] = mono_metadata_type_dup (NULL, (MonoType*)l->data);
+                       header->locals [i] = (MonoType*)l->data;
                }
 #endif
        }
 
+#ifndef DISABLE_JIT
+       /* Free the locals list so mono_mb_free () doesn't free the types twice */
+       g_list_free (mb->locals_list);
+       mb->locals_list = NULL;
+#endif
+
        method->signature = signature;
        if (!signature->hasthis)
                method->flags |= METHOD_ATTRIBUTE_STATIC;
@@ -269,12 +282,19 @@ int
 mono_mb_add_local (MonoMethodBuilder *mb, MonoType *type)
 {
        int res;
+       MonoType *t;
+
+       /*
+        * Have to make a copy early since type might be sig->ret,
+        * which is transient, see mono_metadata_signature_dup_internal_with_padding ().
+        */
+       t = mono_metadata_type_dup (NULL, type);
 
        g_assert (mb != NULL);
        g_assert (type != NULL);
 
        res = mb->locals;
-       mb->locals_list = g_list_append (mb->locals_list, type);
+       mb->locals_list = g_list_append (mb->locals_list, t);
        mb->locals++;
 
        return res;
index fc7f7b18810ca84844177bc7fd22668f850263fd..510d1c18bcd31b3fcd86556f7ee0cea21b4fe0ef 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index d7115994b84f49a9063db8720ace9c9423c44f15..5ccb938df9b03a0f8dfb9a77c6a8accb80e9c2f0 100644 (file)
@@ -5,6 +5,7 @@
  *   Rodrigo Kumpera (rkumpera@novell.com)
  *
  * Copyright 2010 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -239,6 +240,8 @@ bb_split (MonoSimpleBasicBlock *first, MonoSimpleBasicBlock *hint, MonoSimpleBas
 {
        MonoSimpleBasicBlock *res, *bb = first;
 
+       mono_error_init (error);
+
        if (bb_idx_is_contained (hint, target)) {
                first = hint;
        } else if (hint->next && bb_idx_is_contained (hint->next, target)) {
@@ -335,6 +338,8 @@ bb_formation_il_pass (const unsigned char *start, const unsigned char *end, Mono
        MonoSimpleBasicBlock *branch, *next, *current;
        const MonoOpcode *opcode;
 
+       mono_error_init (error);
+
        current = bb;
 
        while (ip < end) {
@@ -463,6 +468,9 @@ bb_formation_eh_pass (MonoMethodHeader *header, MonoSimpleBasicBlock *bb, MonoSi
 {
        int i;
        int end = header->code_size;
+
+       mono_error_init (error);
+
        /*We must split at all points to verify for targets in the middle of an instruction*/
        for (i = 0; i < header->num_clauses; ++i) {
                MonoExceptionClause *clause = header->clauses + i;
@@ -514,21 +522,13 @@ mono_basic_block_free (MonoSimpleBasicBlock *bb)
  * Return the list of basic blocks of method. Return NULL on failure and set @error.
 */
 MonoSimpleBasicBlock*
-mono_basic_block_split (MonoMethod *method, MonoError *error)
+mono_basic_block_split (MonoMethod *method, MonoError *error, MonoMethodHeader *header)
 {
-       MonoError inner_error;
        MonoSimpleBasicBlock *bb, *root;
        const unsigned char *start, *end;
-       MonoMethodHeader *header = mono_method_get_header_checked (method, &inner_error);
 
        mono_error_init (error);
 
-       if (!header) {
-               mono_error_set_not_verifiable (error, method, "Could not decode header due to %s", mono_error_get_message (&inner_error));
-               mono_error_cleanup (&inner_error);
-               return NULL;
-       }
-
        start = header->code;
        end = start + header->code_size;
 
@@ -553,11 +553,9 @@ mono_basic_block_split (MonoMethod *method, MonoError *error)
        dump_bb_list (bb, &root, g_strdup_printf("AFTER LIVENESS %s", mono_method_full_name (method, TRUE)));
 #endif
 
-       mono_metadata_free_mh (header);
        return bb;
 
 fail:
-       mono_metadata_free_mh (header);
        mono_basic_block_free (bb);
        return NULL;
 }
index a971b36176efe2b7badb6cdf4d6f29c53d0e3aa3..a3f65187873add05800f1a59f35fb1912c01d817 100644 (file)
@@ -19,7 +19,7 @@ struct _MonoSimpleBasicBlock {
 };
 
 MonoSimpleBasicBlock*
-mono_basic_block_split (MonoMethod *method, MonoError *error);
+mono_basic_block_split (MonoMethod *method, MonoError *error, MonoMethodHeader *header);
 
 void
 mono_basic_block_free (MonoSimpleBasicBlock *bb);
index 01e2773a9b81ea9b3868e1c1104d6f3b5d0793ac..ece67d1286cd4fef23ca0b3389e7af6b58171f82 100644 (file)
@@ -2,6 +2,7 @@
  * mono-config-dirs.c:
  *
  * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index 2eba9e86d4bc38ba7efe34478ea6630b2e6889ac..80261f2b62e9a3d74741b48af5aff8fb135903b9 100644 (file)
@@ -7,6 +7,7 @@
  *
  * Copyright 2002-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 #include <glib.h>
index 09c55b3bcc8486be2385d9e3ea800cd4f954af0c..b88b20e03819cb0383c8b5af48622205cd8f7524 100644 (file)
@@ -7,6 +7,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 23b6fe7b3caffab9839fab0fd6ef704492a24b4f..a4c48f1413dda3adef0ed9064d111854343a075e 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include "mono-endian.h"
index e07f8fadb838dcd599922996f8b077333134d56d..60c3328a238782269a18de0e1c9bf04ddef6aa52 100644 (file)
@@ -5,6 +5,7 @@
  *   Paolo Molaro (lupus@xamarin.com)
  *
  * Copyright 2013 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_G_HASH_H__
index 7e90b652dd5901714b31f60bfb95725fd85a8404..657800afbe35e70255efb0f3588a9a41f7ef0225 100644 (file)
@@ -5,6 +5,7 @@
  *   Paolo Molaro (lupus@ximian.com)
  *
  * Copyright 2006-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/metadata/mono-mlist.h"
index 267f87d47350f6da4ff85b3c4f966a2d6c63e8e6..fb205e80eaff2781966cdb448262ac85e9bac19f 100644 (file)
@@ -7,6 +7,7 @@
  *
  * Copyright 2008-2009 Novell, Inc (http://www.novell.com)
  * 2011 Xamarin, Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -501,7 +502,12 @@ mono_determine_physical_ram_available_size (void)
        mach_port_t host = mach_host_self();
        vm_size_t page_size;
        vm_statistics_data_t vmstat;
-       if (KERN_SUCCESS != host_statistics(host, HOST_VM_INFO, (host_info_t)&vmstat, &count)) {
+       kern_return_t ret;
+       do {
+               ret = host_statistics(host, HOST_VM_INFO, (host_info_t)&vmstat, &count);
+       } while (ret == KERN_ABORTED);
+
+       if (ret != KERN_SUCCESS) {
                g_warning ("Mono was unable to retrieve memory usage!");
                return 0;
        }
@@ -1584,16 +1590,25 @@ mono_perfcounter_instance_exists (MonoString *instance, MonoString *category, Mo
 MonoArray*
 mono_perfcounter_category_names (MonoString *machine)
 {
+       MonoError error;
        int i;
        MonoArray *res;
        MonoDomain *domain = mono_domain_get ();
        GSList *custom_categories, *tmp;
        /* no support for counters on other machines */
-       if (mono_string_compare_ascii (machine, "."))
-               return mono_array_new (domain, mono_get_string_class (), 0);
+       if (mono_string_compare_ascii (machine, ".")) {
+               res = mono_array_new_checked (domain, mono_get_string_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
+       }
        perfctr_lock ();
        custom_categories = get_custom_categories ();
-       res = mono_array_new (domain, mono_get_string_class (), NUM_CATEGORIES + g_slist_length (custom_categories));
+       res = mono_array_new_checked (domain, mono_get_string_class (), NUM_CATEGORIES + g_slist_length (custom_categories), &error);
+       if (mono_error_set_pending_exception (&error)) {
+               perfctr_unlock ();
+               return NULL;
+       }
+
        for (i = 0; i < NUM_CATEGORIES; ++i) {
                const CategoryDesc *cdesc = &predef_categories [i];
                mono_array_setref (res, i, mono_string_new (domain, cdesc->name));
@@ -1611,17 +1626,23 @@ mono_perfcounter_category_names (MonoString *machine)
 MonoArray*
 mono_perfcounter_counter_names (MonoString *category, MonoString *machine)
 {
+       MonoError error;
        int i;
        SharedCategory *scat;
        const CategoryDesc *cdesc;
        MonoArray *res;
        MonoDomain *domain = mono_domain_get ();
        /* no support for counters on other machines */
-       if (mono_string_compare_ascii (machine, "."))
-               return mono_array_new (domain, mono_get_string_class (), 0);
+       if (mono_string_compare_ascii (machine, ".")) {
+               res =  mono_array_new_checked (domain, mono_get_string_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
+       }
        cdesc = find_category (category);
        if (cdesc) {
-               res = mono_array_new (domain, mono_get_string_class (), cdesc [1].first_counter - cdesc->first_counter);
+               res = mono_array_new_checked (domain, mono_get_string_class (), cdesc [1].first_counter - cdesc->first_counter, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
                for (i = cdesc->first_counter; i < cdesc [1].first_counter; ++i) {
                        const CounterDesc *desc = &predef_counters [i];
                        mono_array_setref (res, i - cdesc->first_counter, mono_string_new (domain, desc->name));
@@ -1633,7 +1654,12 @@ mono_perfcounter_counter_names (MonoString *category, MonoString *machine)
        if (scat) {
                char *p = custom_category_counters (scat);
                int i;
-               res = mono_array_new (domain, mono_get_string_class (), scat->num_counters);
+               res = mono_array_new_checked (domain, mono_get_string_class (), scat->num_counters, &error);
+               if (mono_error_set_pending_exception (&error)) {
+                       perfctr_unlock ();
+                       return NULL;
+               }
+
                for (i = 0; i < scat->num_counters; ++i) {
                        mono_array_setref (res, i, mono_string_new (domain, p + 1));
                        p += 2; /* skip counter type */
@@ -1644,15 +1670,19 @@ mono_perfcounter_counter_names (MonoString *category, MonoString *machine)
                return res;
        }
        perfctr_unlock ();
-       return mono_array_new (domain, mono_get_string_class (), 0);
+       res = mono_array_new_checked (domain, mono_get_string_class (), 0, &error);
+       mono_error_set_pending_exception (&error);
+       return res;
 }
 
 static MonoArray*
-get_string_array (void **array, int count, gboolean is_process)
+get_string_array (void **array, int count, gboolean is_process, MonoError *error)
 {
        int i;
        MonoDomain *domain = mono_domain_get ();
-       MonoArray * res = mono_array_new (mono_domain_get (), mono_get_string_class (), count);
+       mono_error_init (error);
+       MonoArray * res = mono_array_new_checked (mono_domain_get (), mono_get_string_class (), count, error);
+       return_val_if_nok (error, NULL);
        for (i = 0; i < count; ++i) {
                char buf [128];
                char *p;
@@ -1671,11 +1701,13 @@ get_string_array (void **array, int count, gboolean is_process)
 }
 
 static MonoArray*
-get_string_array_of_strings (void **array, int count)
+get_string_array_of_strings (void **array, int count, MonoError *error)
 {
        int i;
        MonoDomain *domain = mono_domain_get ();
-       MonoArray * res = mono_array_new (mono_domain_get (), mono_get_string_class (), count);
+       mono_error_init (error);
+       MonoArray * res = mono_array_new_checked (mono_domain_get (), mono_get_string_class (), count, error);
+       return_val_if_nok (error, NULL);
        for (i = 0; i < count; ++i) {
                char* p = (char *)array[i];
                mono_array_setref (res, i, mono_string_new (domain, p));
@@ -1685,76 +1717,84 @@ get_string_array_of_strings (void **array, int count)
 }
 
 static MonoArray*
-get_mono_instances (void)
+get_mono_instances (MonoError *error)
 {
        int count = 64;
        int res;
        void **buf = NULL;
        MonoArray *array;
+       mono_error_init (error);
        do {
                count *= 2;
                g_free (buf);
                buf = g_new (void*, count);
                res = mono_shared_area_instances (buf, count);
        } while (res == count);
-       array = get_string_array (buf, res, TRUE);
+       array = get_string_array (buf, res, TRUE, error);
        g_free (buf);
        return array;
 }
 
 static MonoArray*
-get_cpu_instances (void)
+get_cpu_instances (MonoError *error)
 {
        void **buf = NULL;
        int i, count;
        MonoArray *array;
-
+       mono_error_init (error);
        count = mono_cpu_count () + 1; /* +1 for "_Total" */
        buf = g_new (void*, count);
        for (i = 0; i < count; ++i)
                buf [i] = GINT_TO_POINTER (i - 1); /* -1 => _Total */
-       array = get_string_array (buf, count, FALSE);
+       array = get_string_array (buf, count, FALSE, error);
        g_free (buf);
        mono_array_setref (array, 0, mono_string_new (mono_domain_get (), "_Total"));
        return array;
 }
 
 static MonoArray*
-get_processes_instances (void)
+get_processes_instances (MonoError *error)
 {
        MonoArray *array;
        int count = 0;
        void **buf = mono_process_list (&count);
+       mono_error_init (error);
        if (!buf)
-               return get_string_array (NULL, 0, FALSE);
-       array = get_string_array (buf, count, TRUE);
+               return get_string_array (NULL, 0, FALSE, error);
+       array = get_string_array (buf, count, TRUE, error);
        g_free (buf);
        return array;
 }
 
 static MonoArray*
-get_networkinterface_instances (void)
+get_networkinterface_instances (MonoError *error)
 {
        MonoArray *array;
        int count = 0;
+       mono_error_init (error);
        void **buf = mono_networkinterface_list (&count);
        if (!buf)
-               return get_string_array_of_strings (NULL, 0);
-       array = get_string_array_of_strings (buf, count);
+               return get_string_array_of_strings (NULL, 0, error);
+       array = get_string_array_of_strings (buf, count, error);
        g_strfreev ((char **) buf);
        return array;
 }
 
 static MonoArray*
-get_custom_instances (MonoString *category)
+get_custom_instances (MonoString *category, MonoError *error)
 {
        SharedCategory *scat;
+       mono_error_init (error);
        scat = find_custom_category (category);
        if (scat) {
                GSList *list = get_custom_instances_list (scat);
                GSList *tmp;
                int i = 0;
-               MonoArray *array = mono_array_new (mono_domain_get (), mono_get_string_class (), g_slist_length (list));
+               MonoArray *array = mono_array_new_checked (mono_domain_get (), mono_get_string_class (), g_slist_length (list), error);
+               if (!is_ok (error)) {
+                       g_slist_free (list);
+                       return NULL;
+               }
                for (tmp = list; tmp; tmp = tmp->next) {
                        SharedInstance *inst = (SharedInstance *)tmp->data;
                        mono_array_setref (array, i, mono_string_new (mono_domain_get (), inst->instance_name));
@@ -1763,31 +1803,46 @@ get_custom_instances (MonoString *category)
                g_slist_free (list);
                return array;
        }
-       return mono_array_new (mono_domain_get (), mono_get_string_class (), 0);
+       return mono_array_new_checked (mono_domain_get (), mono_get_string_class (), 0, error);
 }
 
 MonoArray*
 mono_perfcounter_instance_names (MonoString *category, MonoString *machine)
 {
+       MonoError error;
        const CategoryDesc* cat;
-       if (mono_string_compare_ascii (machine, "."))
-               return mono_array_new (mono_domain_get (), mono_get_string_class (), 0);
+       MonoArray *result = NULL;
+       if (mono_string_compare_ascii (machine, ".")) {
+               result = mono_array_new_checked (mono_domain_get (), mono_get_string_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
+               return result;
+       }
+       
        cat = find_category (category);
-       if (!cat)
-               return get_custom_instances (category);
+       if (!cat) {
+               MonoArray *result = get_custom_instances (category, &error);
+               mono_error_set_pending_exception (&error);
+               return result;
+       }
        switch (cat->instance_type) {
        case MonoInstance:
-               return get_mono_instances ();
+               result = get_mono_instances (&error);
+               break;
        case CPUInstance:
-               return get_cpu_instances ();
+               result = get_cpu_instances (&error);
+               break;
        case ProcessInstance:
-               return get_processes_instances ();
+               result = get_processes_instances (&error);
+               break;
        case NetworkInterfaceInstance:
-               return get_networkinterface_instances ();
+               result = get_networkinterface_instances (&error);
+               break;
        case ThreadInstance:
        default:
-               return mono_array_new (mono_domain_get (), mono_get_string_class (), 0);
+               result = mono_array_new_checked (mono_domain_get (), mono_get_string_class (), 0, &error);
        }
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 typedef struct {
index b9293154ab106bb781a6e1f8d6ed776c878fd003..b27da358575742b762965b76338ececeb5248327 100644 (file)
@@ -5,6 +5,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifdef HAVE_CONFIG_H
@@ -390,10 +391,10 @@ ves_icall_System_Security_Principal_WindowsIdentity_GetUserToken (MonoString *us
 MonoArray*
 ves_icall_System_Security_Principal_WindowsIdentity_GetRoles (gpointer token) 
 {
+       MonoError error;
        MonoArray *array = NULL;
        MonoDomain *domain = mono_domain_get (); 
 #ifdef HOST_WIN32
-       MonoError error;
        gint32 size = 0;
 
        GetTokenInformation (token, TokenGroups, NULL, size, (PDWORD)&size);
@@ -403,7 +404,11 @@ ves_icall_System_Security_Principal_WindowsIdentity_GetRoles (gpointer token)
                        int i=0;
                        int num = tg->GroupCount;
 
-                       array = mono_array_new (domain, mono_get_string_class (), num);
+                       array = mono_array_new_checked (domain, mono_get_string_class (), num, &error);
+                       if (mono_error_set_pending_exception (&error)) {
+                               g_free (tg);
+                               return NULL;
+                       }
 
                        for (i=0; i < num; i++) {
                                gint32 size = 0;
@@ -430,7 +435,8 @@ ves_icall_System_Security_Principal_WindowsIdentity_GetRoles (gpointer token)
 #endif
        if (!array) {
                /* return empty array of string, i.e. string [0] */
-               array = mono_array_new (domain, mono_get_string_class (), 0);
+               array = mono_array_new_checked (domain, mono_get_string_class (), 0, &error);
+               mono_error_set_pending_exception (&error);
        }
        return array;
 }
index f933e11276f1d54d4e2e3662dcc2d5eafe3e0f6e..7f904f3dec7b08970d31c3b3f6161c8489aed3b7 100644 (file)
@@ -4,6 +4,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index b296ca2e37d7f86340bebed513b1dbb548a3552a..48084d143eb540991da6643180b4e23853536676 100644 (file)
@@ -5,6 +5,7 @@
  *     Ludovic Henry (ludovic@xamarin.com)
  *
  * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 //
index b7ab37ea690fac711a97b23898f462e9312ca9b1..e6fca9fba94f2d7e2762b7aae438b38705c00b62 100644 (file)
 #include "mono/utils/mono-tls.h"
 #include "mono/utils/mono-coop-mutex.h"
 
-#if 1
-#ifdef __GNUC__
-#define mono_assert(expr)                 G_STMT_START{                  \
-     if (!(expr))                                                        \
-       {                                                                 \
-               MonoException *ex;                                        \
-               char *msg = g_strdup_printf ("file %s: line %d (%s): "    \
-               "assertion failed: (%s)", __FILE__, __LINE__,             \
-               __PRETTY_FUNCTION__, #expr);                              \
-               ex = mono_get_exception_execution_engine (msg);           \
-               g_free (msg);                                             \
-               mono_raise_exception (ex);                                \
-       };                              }G_STMT_END
-
-#define mono_assert_not_reached()                G_STMT_START{           \
-     MonoException *ex;                                                          \
-     char *msg = g_strdup_printf ("file %s: line %d (%s): "              \
-     "should not be reached", __FILE__, __LINE__, __PRETTY_FUNCTION__);          \
-     ex = mono_get_exception_execution_engine (msg);                     \
-     g_free (msg);                                                       \
-     mono_raise_exception (ex);                                                  \
-}G_STMT_END
-#else /* not GNUC */
-#define mono_assert(expr)                 G_STMT_START{                  \
-     if (!(expr))                                                        \
-       {                                                                 \
-               MonoException *ex;                                        \
-               char *msg = g_strdup_printf ("file %s: line %d: "         \
-               "assertion failed: (%s)", __FILE__, __LINE__,             \
-               #expr);                                                   \
-               ex = mono_get_exception_execution_engine (msg);           \
-               g_free (msg);                                             \
-               mono_raise_exception (ex);                                \
-       };                              }G_STMT_END
-
-#define mono_assert_not_reached()                G_STMT_START{           \
-     MonoException *ex;                                                          \
-     char *msg = g_strdup_printf ("file %s: line %d): "                          \
-     "should not be reached", __FILE__, __LINE__);                       \
-     ex = mono_get_exception_execution_engine (msg);                     \
-     g_free (msg);                                                       \
-     mono_raise_exception (ex);                                                  \
-}G_STMT_END
-#endif
-#else
-#define mono_assert(expr) g_assert(expr)
-#define mono_assert_not_reached() g_assert_not_reached() 
-#endif
-
 /* Use this as MONO_CHECK_ARG_NULL (arg,expr,) in functions returning void */
 #define MONO_CHECK_ARG(arg, expr, retval)              G_STMT_START{             \
                if (G_UNLIKELY (!(expr)))                                                         \
                        }; \
                        tmp_klass; })
 /* eclass should be a run-time constant */
-#define mono_array_new_cached(domain, eclass, size) ({ \
-                       MonoError __error;      \
+#define mono_array_new_cached(domain, eclass, size, error) ({  \
                        MonoVTable *__vtable = mono_class_vtable ((domain), mono_array_class_get_cached ((eclass), 1)); \
-                       MonoArray *__arr = mono_array_new_specific_checked (__vtable, (size), &__error);        \
-                       mono_error_raise_exception (&__error); /* FIXME don't raise here */     \
+                       MonoArray *__arr = mono_array_new_specific_checked (__vtable, (size), (error)); \
                        __arr; })
 
 #else
 
 #define mono_class_get_field_from_name_cached(klass,name) mono_class_get_field_from_name ((klass), (name))
 #define mono_array_class_get_cached(eclass,rank) mono_array_class_get ((eclass), (rank))
-#define mono_array_new_cached(domain, eclass, size) mono_array_new_specific (mono_class_vtable ((domain), mono_array_class_get_cached ((eclass), 1)), (size))
+#define mono_array_new_cached(domain, eclass, size, error) mono_array_new_specific_checked (mono_class_vtable ((domain), mono_array_class_get_cached ((eclass), 1)), (size), (error))
 
 #endif
 
@@ -250,23 +199,24 @@ typedef struct {
 
 struct _MonoException {
        MonoObject object;
+       MonoString *class_name;
+       MonoString *message;
+       MonoObject *_data;
+       MonoObject *inner_ex;
+       MonoString *help_link;
        /* Stores the IPs and the generic sharing infos
           (vtable/MRGCTX) of the frames. */
        MonoArray  *trace_ips;
-       MonoObject *inner_ex;
-       MonoString *message;
-       MonoString *help_link;
-       MonoString *class_name;
        MonoString *stack_trace;
        MonoString *remote_stack_trace;
        gint32      remote_stack_index;
+       /* Dynamic methods referenced by the stack trace */
+       MonoObject *dynamic_methods;
        gint32      hresult;
        MonoString *source;
-       MonoObject *_data;
+       MonoObject *serialization_manager;
        MonoObject *captured_traces;
        MonoArray  *native_trace_ips;
-       /* Dynamic methods referenced by the stack trace */
-       MonoObject *dynamic_methods;
 };
 
 typedef struct {
@@ -650,7 +600,7 @@ MonoObject *
 ves_icall_System_Runtime_Remoting_Messaging_AsyncResult_Invoke (MonoAsyncResult *ares);
 
 MonoWaitHandle *
-mono_wait_handle_new       (MonoDomain *domain, HANDLE handle);
+mono_wait_handle_new       (MonoDomain *domain, HANDLE handle, MonoError *error);
 
 HANDLE
 mono_wait_handle_get_handle (MonoWaitHandle *handle);
@@ -668,7 +618,7 @@ mono_method_call_message_new (MonoMethod *method, gpointer *params, MonoMethod *
                              MonoDelegate **cb, MonoObject **state);
 
 void
-mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoArray *out_args);
+mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoArray *out_args, MonoError *error);
 
 void
 mono_delegate_ctor_with_method (MonoObject *this_obj, MonoObject *target, gpointer addr, MonoMethod *method);
@@ -734,17 +684,6 @@ mono_domain_get_tls_offset (void);
 
 #define IS_MONOTYPE(obj) (!(obj) || (((MonoObject*)(obj))->vtable->klass->image == mono_defaults.corlib && ((MonoReflectionType*)(obj))->type != NULL))
 
-/* 
- * Make sure the argument, which should be a System.Type is a System.MonoType object 
- * or equivalent, and not an instance of 
- * a user defined subclass of System.Type. This should be used in places were throwing
- * an exception is safe.
- */
-#define CHECK_MONOTYPE(obj) do { \
-       if (!IS_MONOTYPE (obj)) \
-               mono_raise_exception (mono_get_exception_not_supported ("User defined subclasses of System.Type are not yet supported")); \
-       } while (0)
-
 /* This should be used for accessing members of Type[] arrays */
 #define mono_type_array_get(arr,index) monotype_cast (mono_array_get ((arr), gpointer, (index)))
 
@@ -1407,11 +1346,11 @@ void        mono_reflection_create_internal_class (MonoReflectionTypeBuilder *tb
 
 void        mono_reflection_setup_generic_class   (MonoReflectionTypeBuilder *tb);
 
-void        mono_reflection_create_generic_class  (MonoReflectionTypeBuilder *tb);
+gboolean    mono_reflection_create_generic_class  (MonoReflectionTypeBuilder *tb, MonoError *error);
 
 MonoReflectionType* mono_reflection_create_runtime_class  (MonoReflectionTypeBuilder *tb);
 
-void        mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides);
+void        mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides, MonoError *error);
 
 void mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *m);
 void mono_reflection_destroy_dynamic_method (MonoReflectionDynamicMethod *mb);
@@ -1428,7 +1367,7 @@ MonoArray* mono_param_get_objects_internal  (MonoDomain *domain, MonoMethod *met
 MonoClass*
 mono_class_bind_generic_parameters (MonoClass *klass, int type_argc, MonoType **types, gboolean is_dynamic);
 MonoType*
-mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc, MonoType **types);
+mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc, MonoType **types, MonoError *error);
 MonoReflectionMethod*
 mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *method, MonoArray *types);
 void
@@ -1443,16 +1382,16 @@ MonoArray  *mono_reflection_sighelper_get_signature_field (MonoReflectionSigHelp
 MonoReflectionMarshalAsAttribute* mono_reflection_marshal_as_attribute_from_marshal_spec (MonoDomain *domain, MonoClass *klass, MonoMarshalSpec *spec, MonoError *error);
 
 gpointer
-mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context);
+mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context, MonoError *error);
 
 gboolean
-mono_reflection_call_is_assignable_to (MonoClass *klass, MonoClass *oklass);
+mono_reflection_call_is_assignable_to (MonoClass *klass, MonoClass *oklass, MonoError *error);
 
 gboolean
 mono_reflection_is_valid_dynamic_token (MonoDynamicImage *image, guint32 token);
 
 void
-mono_reflection_resolve_custom_attribute_data (MonoReflectionMethod *method, MonoReflectionAssembly *assembly, gpointer data, guint32 data_length, MonoArray **ctor_args, MonoArray ** named_args);
+ves_icall_System_Reflection_CustomAttributeData_ResolveArgumentsInternal (MonoReflectionMethod *method, MonoReflectionAssembly *assembly, gpointer data, guint32 data_length, MonoArray **ctor_args, MonoArray ** named_args);
 
 MonoType*
 mono_reflection_type_get_handle (MonoReflectionType *ref, MonoError *error);
@@ -1477,7 +1416,10 @@ mono_string_to_utf8_image (MonoImage *image, MonoString *s, MonoError *error);
 
 
 MonoArray*
-mono_array_clone_in_domain (MonoDomain *domain, MonoArray *array);
+mono_array_clone_in_domain (MonoDomain *domain, MonoArray *array, MonoError *error);
+
+MonoArray*
+mono_array_clone_checked (MonoArray *array, MonoError *error);
 
 void
 mono_array_full_copy (MonoArray *src, MonoArray *dest);
@@ -1485,12 +1427,18 @@ mono_array_full_copy (MonoArray *src, MonoArray *dest);
 gboolean
 mono_array_calc_byte_len (MonoClass *klass, uintptr_t len, uintptr_t *res);
 
+MonoArray*
+mono_array_new_checked (MonoDomain *domain, MonoClass *eclass, uintptr_t n, MonoError *error);
+
 MonoArray*
 mono_array_new_full_checked (MonoDomain *domain, MonoClass *array_class, uintptr_t *lengths, intptr_t *lower_bounds, MonoError *error);
 
 MonoArray*
 mono_array_new_specific_checked (MonoVTable *vtable, uintptr_t n, MonoError *error);
 
+MonoArray*
+ves_icall_array_new (MonoDomain *domain, MonoClass *eclass, uintptr_t n);
+
 MonoArray*
 ves_icall_array_new_specific (MonoVTable *vtable, uintptr_t n);
 
@@ -1503,6 +1451,26 @@ mono_remote_class_vtable (MonoDomain *domain, MonoRemoteClass *remote_class, Mon
 
 void
 mono_upgrade_remote_class (MonoDomain *domain, MonoObject *tproxy, MonoClass *klass);
+
+void*
+mono_load_remote_field_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, void **res, MonoError *error);
+
+MonoObject *
+mono_load_remote_field_new_icall (MonoObject *this_obj, MonoClass *klass, MonoClassField *field);
+
+MonoObject *
+mono_load_remote_field_new_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoError *error);
+
+gboolean
+mono_store_remote_field_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, void* val, MonoError *error);
+
+void
+mono_store_remote_field_new_icall (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg);
+
+gboolean
+mono_store_remote_field_new_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg, MonoError *error);
+
+
 #endif
 
 gpointer
@@ -1514,8 +1482,11 @@ mono_get_addr_from_ftnptr (gpointer descr);
 void
 mono_nullable_init (guint8 *buf, MonoObject *value, MonoClass *klass);
 
+MonoObject *
+mono_value_box_checked (MonoDomain *domain, MonoClass *klass, void* val, MonoError *error);
+
 MonoObject*
-mono_nullable_box (guint8 *buf, MonoClass *klass);
+mono_nullable_box (guint8 *buf, MonoClass *klass, MonoError *error);
 
 #ifdef MONO_SMALL_CONFIG
 #define MONO_IMT_SIZE 9
@@ -1600,7 +1571,7 @@ gsize*
 mono_class_compute_bitmap (MonoClass *klass, gsize *bitmap, int size, int offset, int *max_set, gboolean static_fields);
 
 MonoObject*
-mono_object_xdomain_representation (MonoObject *obj, MonoDomain *target_domain, MonoObject **exc);
+mono_object_xdomain_representation (MonoObject *obj, MonoDomain *target_domain, MonoError *error);
 
 gboolean
 mono_class_is_reflection_method_or_constructor (MonoClass *klass);
@@ -1642,6 +1613,12 @@ mono_vtable_get_static_field_data (MonoVTable *vt);
 MonoObject *
 mono_field_get_value_object_checked (MonoDomain *domain, MonoClassField *field, MonoObject *obj, MonoError *error);
 
+gboolean
+mono_property_set_value_checked (MonoProperty *prop, void *obj, void **params, MonoError *error);
+
+MonoObject*
+mono_property_get_value_checked (MonoProperty *prop, void *obj, void **params, MonoError *error);
+
 char *
 mono_string_to_utf8_ignore (MonoString *s);
 
@@ -1672,11 +1649,11 @@ mono_copy_value (MonoType *type, void *dest, void *value, int deref_pointer);
 void
 mono_error_raise_exception (MonoError *target_error);
 
-void
+gboolean
 mono_error_set_pending_exception (MonoError *error);
 
 MonoArray *
-mono_glist_to_array (GList *list, MonoClass *eclass);
+mono_glist_to_array (GList *list, MonoClass *eclass, MonoError *error);
 
 MonoObject *
 mono_object_new_checked (MonoDomain *domain, MonoClass *klass, MonoError *error);
@@ -1693,9 +1670,18 @@ ves_icall_object_new_fast (MonoVTable *vtable);
 MonoObject *
 mono_object_clone_checked (MonoObject *obj, MonoError *error);
 
+MonoObject *
+mono_object_isinst_checked (MonoObject *obj, MonoClass *klass, MonoError *error);
+
+MonoObject *
+mono_object_isinst_mbyref_checked   (MonoObject *obj, MonoClass *klass, MonoError *error);
+
 MonoString *
 mono_string_new_size_checked (MonoDomain *domain, gint32 len, MonoError *error);
 
+MonoString*
+mono_string_new_len_checked (MonoDomain *domain, const char *text, guint length, MonoError *error);
+
 MonoString*
 mono_string_new_checked (MonoDomain *domain, const char *text, MonoError *merror);
 
@@ -1712,6 +1698,9 @@ MonoObject*
 mono_runtime_invoke_checked (MonoMethod *method, void *obj, void **params, MonoError *error);
 
 
+MonoArray*
+mono_runtime_get_main_args_checked (MonoError *error);
+
 #endif /* __MONO_OBJECT_INTERNALS_H__ */
 
 
index a79e3508e0f74967146ae3c0006d437f669a64a8..c032bc0ff585868f3c67cfb9e3512dea1728b2ad 100644 (file)
@@ -17,17 +17,22 @@ Output defines:
 
 HAS_CROSS_COMPILER_OFFSETS - if set, it means we found some cross offsets, it doesnt mean we'll use it.
 USED_CROSS_COMPILER_OFFSETS - if set, it means we used the cross offsets
+
+Environment defines (from config.h and CFLAGS):
+
+MONO_GENERATING_OFFSETS - Set by an offsets generating tool to disable the usage of any (possibly non-existing) generated header.
+MONO_OFFSETS_FILE - Name of the header file containing the offsets to be used.
+
 */
 
 
 #undef HAS_CROSS_COMPILER_OFFSETS
 #undef USED_CROSS_COMPILER_OFFSETS
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/metadata/object-offsets.h"
+#if !defined (MONO_GENERATING_OFFSETS) && defined (MONO_OFFSETS_FILE)
+#include MONO_OFFSETS_FILE
 #endif
 
-
 #ifndef USED_CROSS_COMPILER_OFFSETS
 
 DECL_ALIGN(gint8)
@@ -180,10 +185,6 @@ DECL_OFFSET(MonoLMF, eip)
 DECL_OFFSET(MonoContext, gregs)
 DECL_OFFSET(MonoContext, fregs)
 
-#ifdef TARGET_WIN32
-DECL_OFFSET(MonoLMF, lmf_addr)
-#endif
-
 DECL_OFFSET(MonoLMF, rsp)
 DECL_OFFSET(MonoLMF, rbp)
 DECL_OFFSET(MonoLMF, rip)
@@ -225,6 +226,18 @@ DECL_OFFSET(DynCallArgs, res2)
 
 #if defined(TARGET_ARM)
 DECL_OFFSET(MonoLMF, method)
+DECL_OFFSET(GSharedVtCallInfo, stack_usage)
+DECL_OFFSET(GSharedVtCallInfo, vret_arg_reg)
+DECL_OFFSET(GSharedVtCallInfo, ret_marshal)
+DECL_OFFSET(GSharedVtCallInfo, vret_slot)
+DECL_OFFSET(GSharedVtCallInfo, gsharedvt_in)
+#endif
+
+#if defined(TARGET_ARM64)
+DECL_OFFSET(GSharedVtCallInfo, stack_usage)
+DECL_OFFSET(GSharedVtCallInfo, gsharedvt_in)
+DECL_OFFSET(GSharedVtCallInfo, ret_marshal)
+DECL_OFFSET(GSharedVtCallInfo, vret_slot)
 #endif
 
 #if defined(TARGET_AMD64) || defined(TARGET_ARM64)
index 81589594b6fa8b0c7c0cf43438c5e0fb9e2bfb1d..cc73d75896fe1a4d77b172366922ee2f01ee47e3 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2001 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #ifdef HAVE_ALLOCA_H
@@ -52,7 +53,7 @@ static void
 get_default_field_value (MonoDomain* domain, MonoClassField *field, void *value);
 
 static MonoString*
-mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig);
+mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig, MonoError *error);
 
 static void
 free_main_args (void);
@@ -627,16 +628,14 @@ mono_compile_method (MonoMethod *method)
 }
 
 gpointer
-mono_runtime_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean add_sync_wrapper)
+mono_runtime_create_jump_trampoline (MonoDomain *domain, MonoMethod *method, gboolean add_sync_wrapper, MonoError *error)
 {
-       MonoError error;
        gpointer res;
 
        MONO_REQ_GC_NEUTRAL_MODE;
 
-       res = callbacks.create_jump_trampoline (domain, method, add_sync_wrapper, &error);
-       if (!mono_error_ok (&error))
-               mono_error_raise_exception (&error); /* FIXME: Don't raise here */
+       mono_error_init (error);
+       res = callbacks.create_jump_trampoline (domain, method, add_sync_wrapper, error);
        return res;
 }
 
@@ -980,7 +979,7 @@ ves_icall_string_alloc (int length)
 {
        MonoError error;
        MonoString *str = mono_string_new_size_checked (mono_domain_get (), length, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return str;
 }
@@ -3506,7 +3505,7 @@ mono_field_get_value_object_checked (MonoDomain *domain, MonoClassField *field,
        klass = mono_class_from_mono_type (type);
 
        if (mono_class_is_nullable (klass))
-               return mono_nullable_box (mono_field_get_addr (obj, vtable, field), klass);
+               return mono_nullable_box (mono_field_get_addr (obj, vtable, field), klass, error);
 
        o = mono_object_new_checked (domain, klass, error);
        return_val_if_nok (error, NULL);
@@ -3528,6 +3527,7 @@ mono_get_constant_value_from_blob (MonoDomain* domain, MonoTypeEnum type, const
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
+       MonoError error;
        int retval = 0;
        const char *p = blob;
        mono_metadata_decode_blob_size (p, &p);
@@ -3558,7 +3558,8 @@ mono_get_constant_value_from_blob (MonoDomain* domain, MonoTypeEnum type, const
                readr8 (p, (double*) value);
                break;
        case MONO_TYPE_STRING:
-               *(gpointer*) value = mono_ldstr_metadata_sig (domain, blob);
+               *(gpointer*) value = mono_ldstr_metadata_sig (domain, blob, &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
                break;
        case MONO_TYPE_CLASS:
                *(gpointer*) value = NULL;
@@ -3655,10 +3656,37 @@ mono_property_set_value (MonoProperty *prop, void *obj, void **params, MonoObjec
        if (exc && *exc == NULL && !mono_error_ok (&error)) {
                *exc = (MonoObject*) mono_error_convert_to_exception (&error);
        } else {
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_error_cleanup (&error);
        }
 }
 
+/**
+ * mono_property_set_value_checked:
+ * @prop: MonoProperty to set
+ * @obj: instance object on which to act
+ * @params: parameters to pass to the propery
+ * @error: set on error
+ *
+ * Invokes the property's set method with the given arguments on the
+ * object instance obj (or NULL for static properties). 
+ * 
+ * Returns: TRUE on success.  On failure returns FALSE and sets @error.
+ * If an exception is thrown, it will be caught and returned via @error.
+ */
+gboolean
+mono_property_set_value_checked (MonoProperty *prop, void *obj, void **params, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
+       MonoObject *exc;
+
+       mono_error_init (error);
+       do_runtime_invoke (prop->set, obj, params, &exc, error);
+       if (exc != NULL && is_ok (error))
+               mono_error_set_exception_instance (error, (MonoException*)exc);
+       return is_ok (error);
+}
+
 /**
  * mono_property_get_value:
  * @prop: MonoProperty to fetch
@@ -3686,12 +3714,43 @@ mono_property_get_value (MonoProperty *prop, void *obj, void **params, MonoObjec
        if (exc && *exc == NULL && !mono_error_ok (&error)) {
                *exc = (MonoObject*) mono_error_convert_to_exception (&error);
        } else {
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_error_cleanup (&error); /* FIXME don't raise here */
        }
 
        return val;
 }
 
+/**
+ * mono_property_get_value_checked:
+ * @prop: MonoProperty to fetch
+ * @obj: instance object on which to act
+ * @params: parameters to pass to the propery
+ * @error: set on error
+ *
+ * Invokes the property's get method with the given arguments on the
+ * object instance obj (or NULL for static properties). 
+ * 
+ * If an exception is thrown, you can't use the
+ * MonoObject* result from the function.  The exception will be propagated via @error.
+ *
+ * Returns: the value from invoking the get method on the property. On
+ * failure returns NULL and sets @error.
+ */
+MonoObject*
+mono_property_get_value_checked (MonoProperty *prop, void *obj, void **params, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
+       MonoObject *exc;
+       MonoObject *val = do_runtime_invoke (prop->get, obj, params, &exc, error);
+       if (exc != NULL && !is_ok (error))
+               mono_error_set_exception_instance (error, (MonoException*) exc);
+       if (!is_ok (error))
+               val = NULL;
+       return val;
+}
+
+
 /*
  * mono_nullable_init:
  * @buf: The nullable structure to initialize.
@@ -3734,17 +3793,17 @@ mono_nullable_init (guint8 *buf, MonoObject *value, MonoClass *klass)
  * mono_nullable_box:
  * @buf: The buffer representing the data to be boxed
  * @klass: the type to box it as.
+ * @error: set on oerr
  *
  * Creates a boxed vtype or NULL from the Nullable structure pointed to by
- * @buf.
+ * @buf.  On failure returns NULL and sets @error
  */
 MonoObject*
-mono_nullable_box (guint8 *buf, MonoClass *klass)
+mono_nullable_box (guint8 *buf, MonoClass *klass, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       MonoError error;
-       
+       mono_error_init (error);
        MonoClass *param_class = klass->cast_class;
 
        mono_class_setup_fields_locking (klass);
@@ -3754,8 +3813,8 @@ mono_nullable_box (guint8 *buf, MonoClass *klass)
        g_assert (mono_class_from_mono_type (klass->fields [1].type) == mono_defaults.boolean_class);
 
        if (*(guint8*)(buf + klass->fields [1].offset - sizeof (MonoObject))) {
-               MonoObject *o = mono_object_new_checked (mono_domain_get (), param_class, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoObject *o = mono_object_new_checked (mono_domain_get (), param_class, error);
+               return_val_if_nok (error, NULL);
                if (param_class->has_references)
                        mono_gc_wbarrier_value_copy (mono_object_unbox (o), buf + klass->fields [0].offset - sizeof (MonoObject), 1, param_class);
                else
@@ -3882,12 +3941,30 @@ MonoArray*
 mono_runtime_get_main_args (void)
 {
        MONO_REQ_GC_UNSAFE_MODE;
+       MonoError error;
+       MonoArray *result = mono_runtime_get_main_args_checked (&error);
+       mono_error_assert_ok (&error);
+       return result;
+}
 
+/**
+ * mono_runtime_get_main_args:
+ * @error: set on error
+ *
+ * Returns: a MonoArray with the arguments passed to the main
+ * program. On failure returns NULL and sets @error.
+ */
+MonoArray*
+mono_runtime_get_main_args_checked (MonoError *error)
+{
        MonoArray *res;
        int i;
        MonoDomain *domain = mono_domain_get ();
 
-       res = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, num_main_args);
+       mono_error_init (error);
+
+       res = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, num_main_args, error);
+       return_val_if_nok (error, NULL);
 
        for (i = 0; i < num_main_args; ++i)
                mono_array_setref (res, i, mono_string_new (domain, main_args [i]));
@@ -3963,6 +4040,7 @@ mono_runtime_run_main (MonoMethod *method, int argc, char* argv[],
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
+       MonoError error;
        int i;
        MonoArray *args = NULL;
        MonoDomain *domain = mono_domain_get ();
@@ -4030,7 +4108,8 @@ mono_runtime_run_main (MonoMethod *method, int argc, char* argv[],
        }
 
        if (sig->param_count) {
-               args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, argc);
+               args = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, argc, &error);
+               mono_error_assert_ok (&error);
                for (i = 0; i < argc; ++i) {
                        /* The encodings should all work, given that
                         * we've checked all these args for the
@@ -4042,7 +4121,8 @@ mono_runtime_run_main (MonoMethod *method, int argc, char* argv[],
                        g_free (str);
                }
        } else {
-               args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, 0);
+               args = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, 0, &error);
+               mono_error_assert_ok (&error);
        }
        
        mono_assembly_set_main (method->klass->image->assembly);
@@ -4123,40 +4203,37 @@ deserialize_object (MonoObject *obj, gboolean *failure, MonoObject **exc)
 
 #ifndef DISABLE_REMOTING
 static MonoObject*
-make_transparent_proxy (MonoObject *obj, gboolean *failure, MonoObject **exc)
+make_transparent_proxy (MonoObject *obj, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
        static MonoMethod *get_proxy_method;
 
-       MonoError error;
        MonoDomain *domain = mono_domain_get ();
        MonoRealProxy *real_proxy;
        MonoReflectionType *reflection_type;
        MonoTransparentProxy *transparent_proxy;
 
+       mono_error_init (error);
+
        if (!get_proxy_method)
                get_proxy_method = mono_class_get_method_from_name (mono_defaults.real_proxy_class, "GetTransparentProxy", 0);
 
        g_assert (mono_class_is_marshalbyref (obj->vtable->klass));
 
-       real_proxy = (MonoRealProxy*) mono_object_new_checked (domain, mono_defaults.real_proxy_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-       reflection_type = mono_type_get_object_checked (domain, &obj->vtable->klass->byval_arg, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       real_proxy = (MonoRealProxy*) mono_object_new_checked (domain, mono_defaults.real_proxy_class, error);
+       return_val_if_nok (error, NULL);
+       reflection_type = mono_type_get_object_checked (domain, &obj->vtable->klass->byval_arg, error);
+       return_val_if_nok (error, NULL);
 
        MONO_OBJECT_SETREF (real_proxy, class_to_proxy, reflection_type);
        MONO_OBJECT_SETREF (real_proxy, unwrapped_server, obj);
 
-       *exc = NULL;
+       MonoObject *exc = NULL;
 
-       transparent_proxy = (MonoTransparentProxy*) mono_runtime_try_invoke (get_proxy_method, real_proxy, NULL, exc, &error);
-       if (*exc == NULL && !mono_error_ok (&error))
-               *exc = (MonoObject*) mono_error_convert_to_exception (&error); /* FIXME change make_transparent_proxy outarg to MonoError */
-       else
-               mono_error_cleanup (&error);
-       if (*exc)
-               *failure = TRUE;
+       transparent_proxy = (MonoTransparentProxy*) mono_runtime_try_invoke (get_proxy_method, real_proxy, NULL, &exc, error);
+       if (exc != NULL && is_ok (error))
+               mono_error_set_exception_instance (error, (MonoException*)exc);
 
        return (MonoObject*) transparent_proxy;
 }
@@ -4166,7 +4243,7 @@ make_transparent_proxy (MonoObject *obj, gboolean *failure, MonoObject **exc)
  * mono_object_xdomain_representation
  * @obj: an object
  * @target_domain: a domain
- * @exc: pointer to a MonoObject*
+ * @error: set on error.
  *
  * Creates a representation of obj in the domain target_domain.  This
  * is either a copy of obj arrived through via serialization and
@@ -4174,36 +4251,37 @@ make_transparent_proxy (MonoObject *obj, gboolean *failure, MonoObject **exc)
  * serializable or marshal by ref.  obj must not be in target_domain.
  *
  * If the object cannot be represented in target_domain, NULL is
- * returned and *exc is set to an appropriate exception.
+ * returned and @error is set appropriately.
  */
 MonoObject*
-mono_object_xdomain_representation (MonoObject *obj, MonoDomain *target_domain, MonoObject **exc)
+mono_object_xdomain_representation (MonoObject *obj, MonoDomain *target_domain, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
+       mono_error_init (error);
        MonoObject *deserialized = NULL;
-       gboolean failure = FALSE;
-
-       g_assert (exc != NULL);
-       *exc = NULL;
 
 #ifndef DISABLE_REMOTING
        if (mono_class_is_marshalbyref (mono_object_class (obj))) {
-               deserialized = make_transparent_proxy (obj, &failure, exc);
+               deserialized = make_transparent_proxy (obj, error);
        } 
        else
 #endif
        {
+               gboolean failure = FALSE;
                MonoDomain *domain = mono_domain_get ();
                MonoObject *serialized;
+               MonoObject *exc = NULL;
 
                mono_domain_set_internal_with_options (mono_object_domain (obj), FALSE);
-               serialized = serialize_object (obj, &failure, exc);
+               serialized = serialize_object (obj, &failure, &exc);
                mono_domain_set_internal_with_options (target_domain, FALSE);
                if (!failure)
-                       deserialized = deserialize_object (serialized, &failure, exc);
+                       deserialized = deserialize_object (serialized, &failure, &exc);
                if (domain != target_domain)
                        mono_domain_set_internal_with_options (domain, FALSE);
+               if (failure)
+                       mono_error_set_exception_instance (error, (MonoException*)exc);
        }
 
        return deserialized;
@@ -4256,14 +4334,15 @@ call_unhandled_exception_delegate (MonoDomain *domain, MonoObject *delegate, Mon
        g_assert (domain == mono_object_domain (domain->domain));
 
        if (mono_object_domain (exc) != domain) {
-               MonoObject *serialization_exc;
+               MonoError error;
 
-               exc = mono_object_xdomain_representation (exc, domain, &serialization_exc);
+               exc = mono_object_xdomain_representation (exc, domain, &error);
                if (!exc) {
-                       if (serialization_exc) {
-                               MonoObject *dummy;
-                               exc = mono_object_xdomain_representation (serialization_exc, domain, &dummy);
-                               g_assert (exc);
+                       if (!is_ok (&error)) {
+                               MonoError inner_error;
+                               MonoException *serialization_exc = mono_error_convert_to_exception (&error);
+                               exc = mono_object_xdomain_representation ((MonoObject*)serialization_exc, domain, &inner_error);
+                               mono_error_assert_ok (&inner_error);
                        } else {
                                exc = (MonoObject*) mono_exception_from_name_msg (mono_get_corlib (),
                                                "System.Runtime.Serialization", "SerializationException",
@@ -4396,7 +4475,9 @@ mono_runtime_exec_managed_code (MonoDomain *domain,
                                MonoMainThreadFunc main_func,
                                gpointer main_args)
 {
-       mono_thread_create (domain, main_func, main_args);
+       MonoError error;
+       mono_thread_create_checked (domain, main_func, main_args, &error);
+       mono_error_assert_ok (&error);
 
        mono_thread_manage ();
 }
@@ -4600,7 +4681,8 @@ mono_runtime_invoke_array (MonoMethod *method, void *obj, MonoArray *params,
                                                 * boxed object in the arg array with the copy.
                                                 */
                                                MonoObject *orig = mono_array_get (params, MonoObject*, i);
-                                               MonoObject *copy = mono_value_box (mono_domain_get (), orig->vtable->klass, mono_object_unbox (orig));
+                                               MonoObject *copy = mono_value_box_checked (mono_domain_get (), orig->vtable->klass, mono_object_unbox (orig), &error);
+                                               mono_error_raise_exception (&error); /* FIXME don't raise here */
                                                mono_array_setref (params, i, copy);
                                        }
                                                
@@ -4652,8 +4734,11 @@ mono_runtime_invoke_array (MonoMethod *method, void *obj, MonoArray *params,
 
                        if (!params)
                                return NULL;
-                       else
-                               return mono_value_box (mono_domain_get (), method->klass->cast_class, pa [0]);
+                       else {
+                               MonoObject *result = mono_value_box_checked (mono_domain_get (), method->klass->cast_class, pa [0], &error);
+                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                               return result;
+                       }
                }
 
                if (!obj) {
@@ -4669,7 +4754,8 @@ mono_runtime_invoke_array (MonoMethod *method, void *obj, MonoArray *params,
                        else
                                o = obj;
                } else if (method->klass->valuetype) {
-                       obj = mono_value_box (mono_domain_get (), method->klass, obj);
+                       obj = mono_value_box_checked (mono_domain_get (), method->klass, obj, &error);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
                }
 
                if (exc) {
@@ -4692,7 +4778,9 @@ mono_runtime_invoke_array (MonoMethod *method, void *obj, MonoArray *params,
                        nullable = mono_object_new_checked (mono_domain_get (), method->klass, &error);
                        mono_error_raise_exception (&error); /* FIXME don't raise here */
 
-                       mono_nullable_init ((guint8 *)mono_object_unbox (nullable), mono_value_box (mono_domain_get (), method->klass->cast_class, obj), method->klass);
+                       MonoObject *boxed = mono_value_box_checked (mono_domain_get (), method->klass->cast_class, obj, &error);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_nullable_init ((guint8 *)mono_object_unbox (nullable), boxed, method->klass);
                        obj = mono_object_unbox (nullable);
                }
 
@@ -4770,7 +4858,7 @@ mono_object_new (MonoDomain *domain, MonoClass *klass)
 
        MonoObject * result = mono_object_new_checked (domain, klass, &error);
 
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -4783,7 +4871,7 @@ ves_icall_object_new (MonoDomain *domain, MonoClass *klass)
 
        MonoObject * result = mono_object_new_checked (domain, klass, &error);
 
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
        return result;
 }
 
@@ -4853,7 +4941,7 @@ mono_object_new_specific (MonoVTable *vtable)
 {
        MonoError error;
        MonoObject *o = mono_object_new_specific_checked (vtable, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return o;
 }
@@ -4881,7 +4969,7 @@ mono_object_new_specific_checked (MonoVTable *vtable, MonoError *error)
 
                        im = mono_class_get_method_from_name (klass, "CreateProxyForType", 1);
                        if (!im) {
-                               mono_error_set_generic_error (error, "System", "NotSupportedException", "Linked away.");
+                               mono_error_set_not_supported (error, "Linked away.");
                                return NULL;
                        }
                        vtable->domain->create_proxy_for_type_method = im;
@@ -4907,7 +4995,7 @@ ves_icall_object_new_specific (MonoVTable *vtable)
 {
        MonoError error;
        MonoObject *o = mono_object_new_specific_checked (vtable, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return o;
 }
@@ -4931,7 +5019,7 @@ mono_object_new_alloc_specific (MonoVTable *vtable)
 {
        MonoError error;
        MonoObject *o = mono_object_new_alloc_specific_checked (vtable, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return o;
 }
@@ -4991,7 +5079,7 @@ mono_object_new_fast (MonoVTable *vtable)
 {
        MonoError error;
        MonoObject *o = mono_object_new_fast_checked (vtable, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return o;
 }
@@ -5035,7 +5123,7 @@ ves_icall_object_new_fast (MonoVTable *vtable)
 {
        MonoError error;
        MonoObject *o = mono_object_new_fast_checked (vtable, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return o;
 }
@@ -5117,11 +5205,11 @@ mono_object_new_from_token  (MonoDomain *domain, MonoImage *image, guint32 token
        MonoClass *klass;
 
        klass = mono_class_get_checked (image, token, &error);
-       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+       mono_error_assert_ok (&error);
        
        result = mono_object_new_checked (domain, klass, &error);
 
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_cleanup (&error);
        return result;
        
 }
@@ -5138,7 +5226,7 @@ mono_object_clone (MonoObject *obj)
 {
        MonoError error;
        MonoObject *o = mono_object_clone_checked (obj, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return o;
 }
@@ -5156,7 +5244,7 @@ mono_object_clone_checked (MonoObject *obj, MonoError *error)
        size = obj->vtable->klass->instance_size;
 
        if (obj->vtable->klass->rank)
-               return (MonoObject*)mono_array_clone ((MonoArray*)obj);
+               return (MonoObject*)mono_array_clone_checked ((MonoArray*)obj, error);
 
        o = (MonoObject *)mono_gc_alloc_obj (obj->vtable, size);
 
@@ -5211,25 +5299,27 @@ mono_array_full_copy (MonoArray *src, MonoArray *dest)
  * mono_array_clone_in_domain:
  * @domain: the domain in which the array will be cloned into
  * @array: the array to clone
+ * @error: set on error
  *
  * This routine returns a copy of the array that is hosted on the
- * specified MonoDomain.
+ * specified MonoDomain.  On failure returns NULL and sets @error.
  */
 MonoArray*
-mono_array_clone_in_domain (MonoDomain *domain, MonoArray *array)
+mono_array_clone_in_domain (MonoDomain *domain, MonoArray *array, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       MonoError error;
        MonoArray *o;
        uintptr_t size, i;
        uintptr_t *sizes;
        MonoClass *klass = array->obj.vtable->klass;
 
+       mono_error_init (error);
+
        if (array->bounds == NULL) {
                size = mono_array_length (array);
-               o = mono_array_new_full_checked (domain, klass, &size, NULL, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               o = mono_array_new_full_checked (domain, klass, &size, NULL, error);
+               return_val_if_nok (error, NULL);
 
                size *= mono_array_element_size (klass);
 #ifdef HAVE_SGEN_GC
@@ -5254,8 +5344,8 @@ mono_array_clone_in_domain (MonoDomain *domain, MonoArray *array)
                size *= array->bounds [i].length;
                sizes [i + klass->rank] = array->bounds [i].lower_bound;
        }
-       o = mono_array_new_full_checked (domain, klass, sizes, (intptr_t*)sizes + klass->rank, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       o = mono_array_new_full_checked (domain, klass, sizes, (intptr_t*)sizes + klass->rank, error);
+       return_val_if_nok (error, NULL);
 #ifdef HAVE_SGEN_GC
        if (klass->element_class->valuetype) {
                if (klass->element_class->has_references)
@@ -5283,7 +5373,26 @@ mono_array_clone (MonoArray *array)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       return mono_array_clone_in_domain (((MonoObject *)array)->vtable->domain, array);
+       MonoError error;
+       MonoArray *result = mono_array_clone_checked (array, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_array_clone_checked:
+ * @array: the array to clone
+ * @error: set on error
+ *
+ * Returns: A newly created array who is a shallow copy of @array.  On
+ * failure returns NULL and sets @error.
+ */
+MonoArray*
+mono_array_clone_checked (MonoArray *array, MonoError *error)
+{
+
+       MONO_REQ_GC_UNSAFE_MODE;
+       return mono_array_clone_in_domain (((MonoObject *)array)->vtable->domain, array, error);
 }
 
 /* helper macros to check for overflow when calculating the size of arrays */
@@ -5340,7 +5449,7 @@ mono_array_new_full (MonoDomain *domain, MonoClass *array_class, uintptr_t *leng
 {
        MonoError error;
        MonoArray *array = mono_array_new_full_checked (domain, array_class, lengths, lower_bounds, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return array;
 }
@@ -5452,17 +5561,43 @@ mono_array_new (MonoDomain *domain, MonoClass *eclass, uintptr_t n)
        MONO_REQ_GC_UNSAFE_MODE;
 
        MonoError error;
+       MonoArray *result = mono_array_new_checked (domain, eclass, n, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_array_new_checked:
+ * @domain: domain where the object is created
+ * @eclass: element class
+ * @n: number of array elements
+ * @error: set on error
+ *
+ * This routine creates a new szarray with @n elements of type @eclass.
+ * On failure returns NULL and sets @error.
+ */
+MonoArray *
+mono_array_new_checked (MonoDomain *domain, MonoClass *eclass, uintptr_t n, MonoError *error)
+{
        MonoClass *ac;
-       MonoArray *arr;
+
+       mono_error_init (error);
 
        ac = mono_array_class_get (eclass, 1);
        g_assert (ac);
 
-       MonoVTable *vtable = mono_class_vtable_full (domain, ac, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoVTable *vtable = mono_class_vtable_full (domain, ac, error);
+       return_val_if_nok (error, NULL);
 
-       arr = mono_array_new_specific_checked (vtable, n, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       return mono_array_new_specific_checked (vtable, n, error);
+}
+
+MonoArray*
+ves_icall_array_new (MonoDomain *domain, MonoClass *eclass, uintptr_t n)
+{
+       MonoError error;
+       MonoArray *arr = mono_array_new_checked (domain, eclass, n, &error);
+       mono_error_set_pending_exception (&error);
 
        return arr;
 }
@@ -5480,7 +5615,7 @@ mono_array_new_specific (MonoVTable *vtable, uintptr_t n)
 {
        MonoError error;
        MonoArray *arr = mono_array_new_specific_checked (vtable, n, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_cleanup (&error);
 
        return arr;
 }
@@ -5519,7 +5654,7 @@ ves_icall_array_new_specific (MonoVTable *vtable, uintptr_t n)
 {
        MonoError error;
        MonoArray *arr = mono_array_new_specific_checked (vtable, n, &error);
-       mono_error_raise_exception (&error);
+       mono_error_set_pending_exception (&error);
 
        return arr;
 }
@@ -5539,7 +5674,7 @@ mono_string_new_utf16 (MonoDomain *domain, const guint16 *text, gint32 len)
        MonoError error;
        MonoString *res = NULL;
        res = mono_string_new_utf16_checked (domain, text, len, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return res;
 }
@@ -5573,21 +5708,22 @@ mono_string_new_utf16_checked (MonoDomain *domain, const guint16 *text, gint32 l
  * mono_string_new_utf32:
  * @text: a pointer to an utf32 string
  * @len: the length of the string
+ * @error: set on failure.
  *
- * Returns: A newly created string object which contains @text.
+ * Returns: A newly created string object which contains @text. On failure returns NULL and sets @error.
  */
-MonoString *
-mono_string_new_utf32 (MonoDomain *domain, const mono_unichar4 *text, gint32 len)
+static MonoString *
+mono_string_new_utf32_checked (MonoDomain *domain, const mono_unichar4 *text, gint32 len, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       MonoError error;
        MonoString *s;
        mono_unichar2 *utf16_output = NULL;
        gint32 utf16_len = 0;
        GError *gerror = NULL;
        glong items_written;
        
+       mono_error_init (error);
        utf16_output = g_ucs4_to_utf16 (text, len, NULL, &items_written, &gerror);
        
        if (gerror)
@@ -5595,8 +5731,8 @@ mono_string_new_utf32 (MonoDomain *domain, const mono_unichar4 *text, gint32 len
 
        while (utf16_output [utf16_len]) utf16_len++;
        
-       s = mono_string_new_size_checked (domain, utf16_len, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       s = mono_string_new_size_checked (domain, utf16_len, error);
+       return_val_if_nok (error, NULL);
 
        memcpy (mono_string_chars (s), utf16_output, utf16_len * 2);
 
@@ -5605,6 +5741,22 @@ mono_string_new_utf32 (MonoDomain *domain, const mono_unichar4 *text, gint32 len
        return s;
 }
 
+/**
+ * mono_string_new_utf32:
+ * @text: a pointer to an utf32 string
+ * @len: the length of the string
+ *
+ * Returns: A newly created string object which contains @text.
+ */
+MonoString *
+mono_string_new_utf32 (MonoDomain *domain, const mono_unichar4 *text, gint32 len)
+{
+       MonoError error;
+       MonoString *result = mono_string_new_utf32_checked (domain, text, len, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
 /**
  * mono_string_new_size:
  * @text: a pointer to an utf16 string
@@ -5617,7 +5769,7 @@ mono_string_new_size (MonoDomain *domain, gint32 len)
 {
        MonoError error;
        MonoString *str = mono_string_new_size_checked (domain, len, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return str;
 }
@@ -5668,23 +5820,41 @@ mono_string_new_len (MonoDomain *domain, const char *text, guint length)
        MONO_REQ_GC_UNSAFE_MODE;
 
        MonoError error;
+       MonoString *result = mono_string_new_len_checked (domain, text, length, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_string_new_len_checked:
+ * @text: a pointer to an utf8 string
+ * @length: number of bytes in @text to consider
+ * @error: set on error
+ *
+ * Returns: A newly created string object which contains @text. On
+ * failure returns NULL and sets @error.
+ */
+MonoString*
+mono_string_new_len_checked (MonoDomain *domain, const char *text, guint length, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
+       mono_error_init (error);
+
        GError *eg_error = NULL;
        MonoString *o = NULL;
-       guint16 *ut;
+       guint16 *ut = NULL;
        glong items_written;
 
-       mono_error_init (&error);
-
        ut = eg_utf8_to_utf16_with_nuls (text, length, NULL, &items_written, &eg_error);
 
        if (!eg_error)
-               o = mono_string_new_utf16_checked (domain, ut, items_written, &error);
+               o = mono_string_new_utf16_checked (domain, ut, items_written, error);
        else 
                g_error_free (eg_error);
 
        g_free (ut);
 
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
        return o;
 }
 
@@ -5739,7 +5909,6 @@ mono_string_new_checked (MonoDomain *domain, const char *text, MonoError *error)
         g_error_free (eg_error);
 
     g_free (ut);
-    mono_error_raise_exception (error);
     
 /*FIXME g_utf8_get_char, g_utf8_next_char and g_utf8_validate are not part of eglib.*/
 #if 0
@@ -5798,23 +5967,42 @@ mono_string_new_wrapper (const char *text)
 MonoObject *
 mono_value_box (MonoDomain *domain, MonoClass *klass, gpointer value)
 {
-       MONO_REQ_GC_UNSAFE_MODE;
-
        MonoError error;
+       MonoObject *result = mono_value_box_checked (domain, klass, value, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_value_box_checked:
+ * @domain: the domain of the new object
+ * @class: the class of the value
+ * @value: a pointer to the unboxed data
+ * @error: set on error
+ *
+ * Returns: A newly created object which contains @value. On failure
+ * returns NULL and sets @error.
+ */
+MonoObject *
+mono_value_box_checked (MonoDomain *domain, MonoClass *klass, gpointer value, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
        MonoObject *res;
        int size;
        MonoVTable *vtable;
 
+       mono_error_init (error);
+
        g_assert (klass->valuetype);
        if (mono_class_is_nullable (klass))
-               return mono_nullable_box ((guint8 *)value, klass);
+               return mono_nullable_box ((guint8 *)value, klass, error);
 
        vtable = mono_class_vtable (domain, klass);
        if (!vtable)
                return NULL;
        size = mono_class_instance_size (klass);
-       res = mono_object_new_alloc_specific_checked (vtable, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       res = mono_object_new_alloc_specific_checked (vtable, error);
+       return_val_if_nok (error, NULL);
 
        size = size - sizeof (MonoObject);
 
@@ -5844,8 +6032,8 @@ mono_value_box (MonoDomain *domain, MonoClass *klass, gpointer value)
 #endif
 #endif
        if (klass->has_finalize) {
-               mono_object_register_finalizer (res, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_object_register_finalizer (res, error);
+               return_val_if_nok (error, NULL);
        }
        return res;
 }
@@ -5970,18 +6158,45 @@ mono_object_unbox (MonoObject *obj)
  * @obj: an object
  * @klass: a pointer to a class 
  *
- * Returns: @obj if @obj is derived from @klass
+ * Returns: @obj if @obj is derived from @klass or NULL otherwise.
  */
 MonoObject *
 mono_object_isinst (MonoObject *obj, MonoClass *klass)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
+       MonoError error;
+       MonoObject *result = mono_object_isinst_checked (obj, klass, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+       
+
+/**
+ * mono_object_isinst_checked:
+ * @obj: an object
+ * @klass: a pointer to a class 
+ * @error: set on error
+ *
+ * Returns: @obj if @obj is derived from @klass or NULL if it isn't.
+ * On failure returns NULL and sets @error.
+ */
+MonoObject *
+mono_object_isinst_checked (MonoObject *obj, MonoClass *klass, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
+       mono_error_init (error);
+       
+       MonoObject *result = NULL;
+
        if (!klass->inited)
                mono_class_init (klass);
 
-       if (mono_class_is_marshalbyref (klass) || (klass->flags & TYPE_ATTRIBUTE_INTERFACE))
-               return mono_object_isinst_mbyref (obj, klass);
+       if (mono_class_is_marshalbyref (klass) || (klass->flags & TYPE_ATTRIBUTE_INTERFACE)) {
+               result = mono_object_isinst_mbyref_checked (obj, klass, error);
+               return result;
+       }
 
        if (!obj)
                return NULL;
@@ -5995,8 +6210,20 @@ mono_object_isinst_mbyref (MonoObject *obj, MonoClass *klass)
        MONO_REQ_GC_UNSAFE_MODE;
 
        MonoError error;
+       MonoObject *result = mono_object_isinst_mbyref_checked (obj, klass, &error);
+       mono_error_cleanup (&error); /* FIXME better API that doesn't swallow the error */
+       return result;
+}
+
+MonoObject *
+mono_object_isinst_mbyref_checked (MonoObject *obj, MonoClass *klass, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
        MonoVTable *vt;
 
+       mono_error_init (error);
+
        if (!obj)
                return NULL;
 
@@ -6030,17 +6257,19 @@ mono_object_isinst_mbyref (MonoObject *obj, MonoClass *klass)
                gpointer pa [2];
 
                im = mono_class_get_method_from_name (rpklass, "CanCastTo", -1);
-               if (!im)
-                       mono_raise_exception (mono_get_exception_not_supported ("Linked away."));
+               if (!im) {
+                       mono_error_set_not_supported (error, "Linked away.");
+                       return NULL;
+               }
                im = mono_object_get_virtual_method (rp, im);
                g_assert (im);
        
-               pa [0] = mono_type_get_object_checked (domain, &klass->byval_arg, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               pa [0] = mono_type_get_object_checked (domain, &klass->byval_arg, error);
+               return_val_if_nok (error, NULL);
                pa [1] = obj;
 
-               res = mono_runtime_invoke_checked (im, rp, pa, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               res = mono_runtime_invoke_checked (im, rp, pa, error);
+               return_val_if_nok (error, NULL);
 
                if (*(MonoBoolean *) mono_object_unbox(res)) {
                        /* Update the vtable of the remote type, so it can safely cast to this new type */
@@ -6057,19 +6286,17 @@ mono_object_isinst_mbyref (MonoObject *obj, MonoClass *klass)
  * @obj: an object
  * @klass: a pointer to a class 
  *
- * Returns: @obj if @obj is derived from @klass, throws an exception otherwise
+ * Returns: @obj if @obj is derived from @klass, returns NULL otherwise.
  */
 MonoObject *
 mono_object_castclass_mbyref (MonoObject *obj, MonoClass *klass)
 {
        MONO_REQ_GC_UNSAFE_MODE;
+       MonoError error;
 
        if (!obj) return NULL;
-       if (mono_object_isinst_mbyref (obj, klass)) return obj;
-               
-       mono_raise_exception (mono_exception_from_name (mono_defaults.corlib,
-                                                       "System",
-                                                       "InvalidCastException"));
+       if (mono_object_isinst_mbyref_checked (obj, klass, &error)) return obj;
+       mono_error_cleanup (&error);
        return NULL;
 }
 
@@ -6232,14 +6459,18 @@ MonoString*
 mono_ldstr (MonoDomain *domain, MonoImage *image, guint32 idx)
 {
        MONO_REQ_GC_UNSAFE_MODE;
+       MonoError error;
 
        if (image->dynamic) {
-               MonoString *str = (MonoString *)mono_lookup_dynamic_token (image, MONO_TOKEN_STRING | idx, NULL);
+               MonoString *str = (MonoString *)mono_lookup_dynamic_token (image, MONO_TOKEN_STRING | idx, NULL, &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
                return str;
        } else {
                if (!mono_verifier_verify_string_signature (image, idx, NULL))
                        return NULL; /*FIXME we should probably be raising an exception here*/
-               return mono_ldstr_metadata_sig (domain, mono_metadata_user_string (image, idx));
+               MonoString *str = mono_ldstr_metadata_sig (domain, mono_metadata_user_string (image, idx), &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               return str;
        }
 }
 
@@ -6247,15 +6478,17 @@ mono_ldstr (MonoDomain *domain, MonoImage *image, guint32 idx)
  * mono_ldstr_metadata_sig
  * @domain: the domain for the string
  * @sig: the signature of a metadata string
+ * @error: set on error
  *
- * Returns: a MonoString for a string stored in the metadata
+ * Returns: a MonoString for a string stored in the metadata. On
+ * failure returns NULL and sets @error.
  */
 static MonoString*
-mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig)
+mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       MonoError error;
+       mono_error_init (error);
        const char *str = sig;
        MonoString *o, *interned;
        size_t len2;
@@ -6263,8 +6496,8 @@ mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig)
        len2 = mono_metadata_decode_blob_size (str, &str);
        len2 >>= 1;
 
-       o = mono_string_new_utf16_checked (domain, (guint16*)str, len2, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       o = mono_string_new_utf16_checked (domain, (guint16*)str, len2, error);
+       return_val_if_nok (error, NULL);
 #if G_BYTE_ORDER != G_LITTLE_ENDIAN
        {
                int i;
@@ -6281,8 +6514,7 @@ mono_ldstr_metadata_sig (MonoDomain *domain, const char* sig)
        if (interned)
                return interned; /* o will get garbage collected */
 
-       o = mono_string_get_pinned (o, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       o = mono_string_get_pinned (o, error);
        if (o) {
                ldstr_lock ();
                interned = (MonoString *)mono_g_hash_table_lookup (domain->ldstr_table, o);
@@ -6656,21 +6888,23 @@ mono_raise_exception_with_context (MonoException *ex, MonoContext *ctx)
  * mono_wait_handle_new:
  * @domain: Domain where the object will be created
  * @handle: Handle for the wait handle
+ * @error: set on error.
  *
- * Returns: A new MonoWaitHandle created in the given domain for the given handle
+ * Returns: A new MonoWaitHandle created in the given domain for the
+ * given handle.  On failure returns NULL and sets @rror.
  */
 MonoWaitHandle *
-mono_wait_handle_new (MonoDomain *domain, HANDLE handle)
+mono_wait_handle_new (MonoDomain *domain, HANDLE handle, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
-       MonoError error;
        MonoWaitHandle *res;
        gpointer params [1];
        static MonoMethod *handle_set;
 
-       res = (MonoWaitHandle *)mono_object_new_checked (domain, mono_defaults.manualresetevent_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_init (error);
+       res = (MonoWaitHandle *)mono_object_new_checked (domain, mono_defaults.manualresetevent_class, error);
+       return_val_if_nok (error, NULL);
 
        /* Even though this method is virtual, it's safe to invoke directly, since the object type matches.  */
        if (!handle_set)
@@ -6678,9 +6912,7 @@ mono_wait_handle_new (MonoDomain *domain, HANDLE handle)
 
        params [0] = &handle;
 
-       mono_runtime_invoke_checked (handle_set, res, params, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-
+       mono_runtime_invoke_checked (handle_set, res, params, error);
        return res;
 }
 
@@ -6752,8 +6984,10 @@ mono_async_result_new (MonoDomain *domain, HANDLE handle, MonoObject *state, gpo
        res->data = (void **)data;
        MONO_OBJECT_SETREF (res, object_data, object_data);
        MONO_OBJECT_SETREF (res, async_state, state);
+       MonoWaitHandle *wait_handle = mono_wait_handle_new (domain, handle, &error);
+       mono_error_raise_exception (&error); /* FIXME don't raise here */
        if (handle != NULL)
-               MONO_OBJECT_SETREF (res, handle, (MonoObject *) mono_wait_handle_new (domain, handle));
+               MONO_OBJECT_SETREF (res, handle, (MonoObject *) wait_handle);
 
        res->sync_completed = FALSE;
        res->completed = FALSE;
@@ -6794,7 +7028,8 @@ ves_icall_System_Runtime_Remoting_Messaging_AsyncResult_Invoke (MonoAsyncResult
 
                if (ac->cb_method) {
                        mono_runtime_invoke_checked (ac->cb_method, ac->cb_target, (gpointer*) &ares, &error);
-                       mono_error_raise_exception (&error);
+                       if (mono_error_set_pending_exception (&error))
+                               return NULL;
                }
        }
 
@@ -6918,7 +7153,7 @@ mono_remoting_invoke (MonoObject *real_proxy, MonoMethodMessage *msg, MonoObject
        if (!im) {
                im = mono_class_get_method_from_name (mono_defaults.real_proxy_class, "PrivateInvoke", 4);
                if (!im) {
-                       mono_error_set_generic_error (error, "System", "NotSupportedException", "Linked away.");
+                       mono_error_set_not_supported (error, "Linked away.");
                        return NULL;
                }
                real_proxy->vtable->domain->private_invoke_method = im;
@@ -7238,9 +7473,10 @@ mono_method_call_message_new (MonoMethod *method, gpointer *params, MonoMethod *
 
                klass = mono_class_from_mono_type (sig->params [i]);
 
-               if (klass->valuetype)
-                       arg = mono_value_box (domain, klass, vpos);
-               else 
+               if (klass->valuetype) {
+                       arg = mono_value_box_checked (domain, klass, vpos, &error);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+               } else 
                        arg = *((MonoObject **)vpos);
                      
                mono_array_setref (msg->args, i, arg);
@@ -7261,10 +7497,12 @@ mono_method_call_message_new (MonoMethod *method, gpointer *params, MonoMethod *
  * Restore results from message based processing back to arguments pointers
  */
 void
-mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoArray *out_args)
+mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoArray *out_args, MonoError *error)
 {
        MONO_REQ_GC_UNSAFE_MODE;
 
+       mono_error_init (error);
+
        MonoMethodSignature *sig = mono_method_signature (method);
        int i, j, type, size, out_len;
        
@@ -7279,8 +7517,10 @@ mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoAr
 
                if (pt->byref) {
                        char *arg;
-                       if (j >= out_len)
-                               mono_raise_exception (mono_get_exception_execution_engine ("The proxy call returned an incorrect number of output arguments"));
+                       if (j >= out_len) {
+                               mono_error_set_execution_engine (error, "The proxy call returned an incorrect number of output arguments");
+                               return;
+                       }
 
                        arg = (char *)mono_array_get (out_args, gpointer, j);
                        type = pt->type;
@@ -7327,11 +7567,36 @@ mono_method_return_message_restore (MonoMethod *method, gpointer *params, MonoAr
 gpointer
 mono_load_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, gpointer *res)
 {
-       MONO_REQ_GC_UNSAFE_MODE;
-
        MonoError error;
+       gpointer result = mono_load_remote_field_checked (this_obj, klass, field, res, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_load_remote_field_checked:
+ * @this: pointer to an object
+ * @klass: klass of the object containing @field
+ * @field: the field to load
+ * @res: a storage to store the result
+ * @error: set on error
+ *
+ * This method is called by the runtime on attempts to load fields of
+ * transparent proxy objects. @this points to such TP, @klass is the class of
+ * the object containing @field. @res is a storage location which can be
+ * used to store the result.
+ *
+ * Returns: an address pointing to the value of field.  On failure returns NULL and sets @error.
+ */
+gpointer
+mono_load_remote_field_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, gpointer *res, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
 
        static MonoMethod *getter = NULL;
+
+       mono_error_init (error);
+
        MonoDomain *domain = mono_domain_get ();
        MonoTransparentProxy *tp = (MonoTransparentProxy *) this_obj;
        MonoClass *field_class;
@@ -7350,17 +7615,20 @@ mono_load_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *
        
        if (!getter) {
                getter = mono_class_get_method_from_name (mono_defaults.object_class, "FieldGetter", -1);
-               if (!getter)
-                       mono_raise_exception (mono_get_exception_not_supported ("Linked away."));
+               if (!getter) {
+                       mono_error_set_not_supported (error, "Linked away.");
+                       return NULL;
+               }
        }
        
        field_class = mono_class_from_mono_type (field->type);
 
-       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-       out_args = mono_array_new (domain, mono_defaults.object_class, 1);
-       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, getter, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, error);
+       return_val_if_nok (error, NULL);
+       out_args = mono_array_new_checked (domain, mono_defaults.object_class, 1, error);
+       return_val_if_nok (error, NULL);
+       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, getter, NULL, error);
+       return_val_if_nok (error, NULL);
        mono_message_init (domain, msg, rm, out_args);
 
        full_name = mono_type_get_full_name (klass);
@@ -7368,15 +7636,18 @@ mono_load_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *
        mono_array_setref (msg->args, 1, mono_string_new (domain, mono_field_get_name (field)));
        g_free (full_name);
 
-       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, error);
+       return_val_if_nok (error, NULL);
 
-       if (exc) mono_raise_exception ((MonoException *)exc);
+       if (exc) {
+               mono_error_set_exception_instance (error, (MonoException *)exc);
+               return NULL;
+       }
 
        if (mono_array_length (out_args) == 0)
                return NULL;
 
-       *res = mono_array_get (out_args, MonoObject *, 0); /* FIXME: GC write abrrier for res */
+       mono_gc_wbarrier_generic_store (res, mono_array_get (out_args, MonoObject *, 0));
 
        if (field_class->valuetype) {
                return ((char *)*res) + sizeof (MonoObject);
@@ -7395,9 +7666,54 @@ mono_load_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *
 MonoObject *
 mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassField *field)
 {
-       MONO_REQ_GC_UNSAFE_MODE;
+       MonoError error;
 
+       MonoObject *result = mono_load_remote_field_new_checked (this_obj, klass, field, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_load_remote_field_new_icall:
+ * @this: pointer to an object
+ * @klass: klass of the object containing @field
+ * @field: the field to load
+ *
+ * This method is called by the runtime on attempts to load fields of
+ * transparent proxy objects. @this points to such TP, @klass is the class of
+ * the object containing @field.
+ * 
+ * Returns: a freshly allocated object containing the value of the
+ * field.  On failure returns NULL and throws an exception.
+ */
+MonoObject *
+mono_load_remote_field_new_icall (MonoObject *this_obj, MonoClass *klass, MonoClassField *field)
+{
        MonoError error;
+       MonoObject *result = mono_load_remote_field_new_checked (this_obj, klass, field, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
+/**
+ * mono_load_remote_field_new_checked:
+ * @this: pointer to an object
+ * @klass: klass of the object containing @field
+ * @field: the field to load
+ * @error: set on error.
+ *
+ * This method is called by the runtime on attempts to load fields of
+ * transparent proxy objects. @this points to such TP, @klass is the class of
+ * the object containing @field.
+ * 
+ * Returns: a freshly allocated object containing the value of the field.  On failure returns NULL and sets @error.
+ */
+MonoObject *
+mono_load_remote_field_new_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
+
+       mono_error_init (error);
 
        static MonoMethod *getter = NULL;
        MonoDomain *domain = mono_domain_get ();
@@ -7415,8 +7731,8 @@ mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFie
        if (mono_class_is_contextbound (tp->remote_class->proxy_class) && tp->rp->context == (MonoObject *) mono_context_get ()) {
                gpointer val;
                if (field_class->valuetype) {
-                       res = mono_object_new_checked (domain, field_class, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       res = mono_object_new_checked (domain, field_class, error);
+                       return_val_if_nok (error, NULL);
                        val = ((gchar *) res) + sizeof (MonoObject);
                } else {
                        val = &res;
@@ -7427,16 +7743,19 @@ mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFie
 
        if (!getter) {
                getter = mono_class_get_method_from_name (mono_defaults.object_class, "FieldGetter", -1);
-               if (!getter)
-                       mono_raise_exception (mono_get_exception_not_supported ("Linked away."));
+               if (!getter) {
+                       mono_error_set_not_supported (error, "Linked away.");
+                       return NULL;
+               }
        }
        
-       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-       out_args = mono_array_new (domain, mono_defaults.object_class, 1);
+       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, error);
+       return_val_if_nok (error, NULL);
+       out_args = mono_array_new_checked (domain, mono_defaults.object_class, 1, error);
+       return_val_if_nok (error, NULL);
 
-       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, getter, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, getter, NULL, error);
+       return_val_if_nok (error, NULL);
        mono_message_init (domain, msg, rm, out_args);
 
        full_name = mono_type_get_full_name (klass);
@@ -7444,10 +7763,13 @@ mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFie
        mono_array_setref (msg->args, 1, mono_string_new (domain, mono_field_get_name (field)));
        g_free (full_name);
 
-       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, error);
+       return_val_if_nok (error, NULL);
 
-       if (exc) mono_raise_exception ((MonoException *)exc);
+       if (exc) {
+               mono_error_set_exception_instance (error, (MonoException *)exc);
+               return NULL;
+       }
 
        if (mono_array_length (out_args) == 0)
                res = NULL;
@@ -7471,11 +7793,33 @@ mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFie
 void
 mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, gpointer val)
 {
-       MONO_REQ_GC_UNSAFE_MODE;
-
        MonoError error;
+       (void) mono_store_remote_field_checked (this_obj, klass, field, val, &error);
+       mono_error_cleanup (&error);
+}
+
+/**
+ * mono_store_remote_field_checked:
+ * @this_obj: pointer to an object
+ * @klass: klass of the object containing @field
+ * @field: the field to load
+ * @val: the value/object to store
+ * @error: set on error
+ *
+ * This method is called by the runtime on attempts to store fields of
+ * transparent proxy objects. @this_obj points to such TP, @klass is the class of
+ * the object containing @field. @val is the new value to store in @field.
+ *
+ * Returns: on success returns TRUE, on failure returns FALSE and sets @error.
+ */
+gboolean
+mono_store_remote_field_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, gpointer val, MonoError *error)
+{
+       
+       MONO_REQ_GC_UNSAFE_MODE;
 
        static MonoMethod *setter = NULL;
+
        MonoDomain *domain = mono_domain_get ();
        MonoTransparentProxy *tp = (MonoTransparentProxy *) this_obj;
        MonoClass *field_class;
@@ -7485,6 +7829,8 @@ mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField
        MonoObject *arg;
        char* full_name;
 
+       mono_error_init (error);
+
        g_assert (mono_object_is_transparent_proxy (this_obj));
 
        field_class = mono_class_from_mono_type (field->type);
@@ -7492,25 +7838,28 @@ mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField
        if (mono_class_is_contextbound (tp->remote_class->proxy_class) && tp->rp->context == (MonoObject *) mono_context_get ()) {
                if (field_class->valuetype) mono_field_set_value (tp->rp->unwrapped_server, field, val);
                else mono_field_set_value (tp->rp->unwrapped_server, field, *((MonoObject **)val));
-               return;
+               return TRUE;
        }
 
        if (!setter) {
                setter = mono_class_get_method_from_name (mono_defaults.object_class, "FieldSetter", -1);
-               if (!setter)
-                       mono_raise_exception (mono_get_exception_not_supported ("Linked away."));
+               if (!setter) {
+                       mono_error_set_not_supported (error, "Linked away.");
+                       return FALSE;
+               }
        }
 
-       if (field_class->valuetype)
-               arg = mono_value_box (domain, field_class, val);
-       else 
+       if (field_class->valuetype) {
+               arg = mono_value_box_checked (domain, field_class, val, error);
+               return_val_if_nok (error, FALSE);
+       } else 
                arg = *((MonoObject **)val);
                
 
-       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, setter, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, error);
+       return_val_if_nok (error, FALSE);
+       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, setter, NULL, error);
+       return_val_if_nok (error, FALSE);
        mono_message_init (domain, msg, rm, NULL);
 
        full_name = mono_type_get_full_name (klass);
@@ -7519,10 +7868,14 @@ mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField
        mono_array_setref (msg->args, 2, arg);
        g_free (full_name);
 
-       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, error);
+       return_val_if_nok (error, FALSE);
 
-       if (exc) mono_raise_exception ((MonoException *)exc);
+       if (exc) {
+               mono_error_set_exception_instance (error, (MonoException *)exc);
+               return FALSE;
+       }
+       return TRUE;
 }
 
 /**
@@ -7537,9 +7890,42 @@ mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField
 void
 mono_store_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg)
 {
-       MONO_REQ_GC_UNSAFE_MODE;
+       MonoError error;
+       (void) mono_store_remote_field_new_checked (this_obj, klass, field, arg, &error);
+       mono_error_cleanup (&error);
+}
 
+/**
+ * mono_store_remote_field_new_icall:
+ * @this_obj:
+ * @klass:
+ * @field:
+ * @arg:
+ *
+ * Missing documentation
+ */
+void
+mono_store_remote_field_new_icall (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg)
+{
        MonoError error;
+       (void) mono_store_remote_field_new_checked (this_obj, klass, field, arg, &error);
+       mono_error_set_pending_exception (&error);
+}
+
+/**
+ * mono_store_remote_field_new_checked:
+ * @this_obj:
+ * @klass:
+ * @field:
+ * @arg:
+ * @error:
+ *
+ * Missing documentation
+ */
+gboolean
+mono_store_remote_field_new_checked (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg, MonoError *error)
+{
+       MONO_REQ_GC_UNSAFE_MODE;
 
        static MonoMethod *setter = NULL;
        MonoDomain *domain = mono_domain_get ();
@@ -7550,6 +7936,8 @@ mono_store_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFi
        MonoObject *exc;
        char* full_name;
 
+       mono_error_init (error);
+
        g_assert (mono_object_is_transparent_proxy (this_obj));
 
        field_class = mono_class_from_mono_type (field->type);
@@ -7557,19 +7945,21 @@ mono_store_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFi
        if (mono_class_is_contextbound (tp->remote_class->proxy_class) && tp->rp->context == (MonoObject *) mono_context_get ()) {
                if (field_class->valuetype) mono_field_set_value (tp->rp->unwrapped_server, field, ((gchar *) arg) + sizeof (MonoObject));
                else mono_field_set_value (tp->rp->unwrapped_server, field, arg);
-               return;
+               return TRUE;
        }
 
        if (!setter) {
                setter = mono_class_get_method_from_name (mono_defaults.object_class, "FieldSetter", -1);
-               if (!setter)
-                       mono_raise_exception (mono_get_exception_not_supported ("Linked away."));
+               if (!setter) {
+                       mono_error_set_not_supported (error, "Linked away.");
+                       return FALSE;
+               }
        }
 
-       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
-       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, setter, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       msg = (MonoMethodMessage *)mono_object_new_checked (domain, mono_defaults.mono_method_message_class, error);
+       return_val_if_nok (error, FALSE);
+       MonoReflectionMethod *rm = mono_method_get_object_checked (domain, setter, NULL, error);
+       return_val_if_nok (error, FALSE);
        mono_message_init (domain, msg, rm, NULL);
 
        full_name = mono_type_get_full_name (klass);
@@ -7578,10 +7968,14 @@ mono_store_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassFi
        mono_array_setref (msg->args, 2, arg);
        g_free (full_name);
 
-       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_remoting_invoke ((MonoObject *)(tp->rp), msg, &exc, &out_args, error);
+       return_val_if_nok (error, FALSE);
 
-       if (exc) mono_raise_exception ((MonoException *)exc);
+       if (exc) {
+               mono_error_set_exception_instance (error, (MonoException *)exc);
+               return FALSE;
+       }
+       return TRUE;
 }
 #endif
 
@@ -7675,17 +8069,19 @@ mono_array_addr_with_size (MonoArray *array, int size, uintptr_t idx)
 
 
 MonoArray *
-mono_glist_to_array (GList *list, MonoClass *eclass) 
+mono_glist_to_array (GList *list, MonoClass *eclass, MonoError *error
 {
        MonoDomain *domain = mono_domain_get ();
        MonoArray *res;
        int len, i;
 
+       mono_error_init (error);
        if (!list)
                return NULL;
 
        len = g_list_length (list);
-       res = mono_array_new (domain, eclass, len);
+       res = mono_array_new_checked (domain, eclass, len, error);
+       return_val_if_nok (error, NULL);
 
        for (i = 0; list; list = list->next, i++)
                mono_array_set (res, gpointer, i, list->data);
index 433938694844601138a58549ed296c236e659c98..99f31507451dfe415d73fa652cc3efefafcf5b9a 100644 (file)
@@ -72,29 +72,37 @@ MONO_API int            mono_string_length (MonoString *s);
 MONO_RT_EXTERNAL_ONLY MONO_API MonoObject *
 mono_object_new                    (MonoDomain *domain, MonoClass *klass);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_new_specific    (MonoVTable *vtable);
 
 /* can be used for classes without finalizer in non-profiling mode */
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_new_fast       (MonoVTable *vtable);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_new_alloc_specific (MonoVTable *vtable);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_new_from_token  (MonoDomain *domain, MonoImage *image, uint32_t token);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*
 mono_array_new             (MonoDomain *domain, MonoClass *eclass, uintptr_t n);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*
 mono_array_new_full        (MonoDomain *domain, MonoClass *array_class,
                             uintptr_t *lengths, intptr_t *lower_bounds);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray *
 mono_array_new_specific            (MonoVTable *vtable, uintptr_t n);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*
 mono_array_clone           (MonoArray *array);
 
@@ -104,9 +112,11 @@ mono_array_addr_with_size   (MonoArray *array, int size, uintptr_t idx);
 MONO_API uintptr_t
 mono_array_length           (MonoArray *array);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoString*
 mono_string_new_utf16      (MonoDomain *domain, const mono_unichar2 *text, int32_t len);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoString*
 mono_string_new_size       (MonoDomain *domain, int32_t len);
 
@@ -126,9 +136,11 @@ mono_string_new                (MonoDomain *domain, const char *text);
 MONO_API MonoString*
 mono_string_new_wrapper            (const char *text);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoString*
 mono_string_new_len        (MonoDomain *domain, const char *text, unsigned int length);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoString*
 mono_string_new_utf32      (MonoDomain *domain, const mono_unichar4 *text, int32_t len);
 
@@ -162,6 +174,7 @@ mono_object_hash            (MonoObject* obj);
 MONO_API MonoString *
 mono_object_to_string (MonoObject *obj, MonoObject **exc);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_value_box             (MonoDomain *domain, MonoClass *klass, void* val);
 
@@ -180,15 +193,19 @@ mono_object_get_class       (MonoObject *obj);
 MONO_API void*
 mono_object_unbox          (MonoObject *obj);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_clone          (MonoObject *obj);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_isinst         (MonoObject *obj, MonoClass *klass);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_isinst_mbyref   (MonoObject *obj, MonoClass *klass);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_object_castclass_mbyref (MonoObject *obj, MonoClass *klass);
 
@@ -246,6 +263,7 @@ mono_runtime_invoke_array   (MonoMethod *method, void *obj, MonoArray *params,
 MONO_API void*
 mono_method_get_unmanaged_thunk (MonoMethod *method);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*
 mono_runtime_get_main_args  (void);
 
@@ -267,15 +285,19 @@ mono_runtime_set_main_args  (int argc, char* argv[]);
 
 /* The following functions won't be available with mono was configured with remoting disabled. */
 /*#ifndef DISABLE_REMOTING */
+MONO_RT_EXTERNAL_ONLY
 MONO_API void*
 mono_load_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, void **res);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_load_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassField *field);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API void
 mono_store_remote_field (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, void* val);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API void
 mono_store_remote_field_new (MonoObject *this_obj, MonoClass *klass, MonoClassField *field, MonoObject *arg);
 
@@ -307,9 +329,11 @@ MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject *
 mono_field_get_value_object (MonoDomain *domain, MonoClassField *field, MonoObject *obj);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API void
 mono_property_set_value (MonoProperty *prop, void *obj, void **params, MonoObject **exc);
 
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoObject*
 mono_property_get_value (MonoProperty *prop, void *obj, void **params, MonoObject **exc);
 
index 6cfbe5cbcce2fe85df1a6912fbcb024ad8401d8e..838142e253f01761818863eade191b0f48381df4 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2002-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <mono/metadata/opcodes.h>
 #include <stddef.h> /* for NULL */
index 19ebb958b24d3e2a1a4981bac8eef93b7674f298..eac9bfba360a0fb62258c16efe8afbcb53206698 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdio.h>
@@ -361,7 +362,6 @@ dump_verify_info (MonoImage *image, int flags)
                for (i = 0; i < m->rows; ++i) {
                        MonoMethod *method;
                        MonoError error;
-                       mono_loader_clear_error ();
 
                        method = mono_get_method_checked (image, MONO_TOKEN_METHOD_DEF | (i+1), NULL, NULL, &error);
                        if (!method) {
@@ -486,16 +486,14 @@ verify_image_file (const char *fname)
                        continue;
                }
                mono_class_init (klass);
-               if (mono_class_has_failure (klass) || mono_loader_get_last_error ()) {
+               if (mono_class_has_failure (klass)) {
                        printf ("Error verifying class(0x%08x) %s.%s a type load error happened\n", token, klass->name_space, klass->name);
-                       mono_loader_clear_error ();
                        ++count;
                }
 
                mono_class_setup_vtable (klass);
-               if (mono_class_has_failure (klass) || mono_loader_get_last_error ()) {
+               if (mono_class_has_failure (klass)) {
                        printf ("Error verifying class(0x%08x) %s.%s a type load error happened\n", token, klass->name_space, klass->name);
-                       mono_loader_clear_error ();
                        ++count;
                }
        }
index dd4ac82ee77f6dd8bb4a9207103b69333f19a6ca..d74ca084f10e586c0521ee9d848db9c1dcf42fbf 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2002 Ximian, Inc.
  * Copyright 2002-2006 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -506,7 +507,9 @@ ves_icall_System_Diagnostics_Process_GetModules_internal (MonoObject *this_obj,
        }
 
        count = module_count + assembly_count; 
-       temp_arr = mono_array_new (mono_domain_get (), mono_class_get_process_module_class (), count);
+       temp_arr = mono_array_new_checked (mono_domain_get (), mono_class_get_process_module_class (), count, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        for (i = 0; i < module_count; i++) {
                if (GetModuleBaseName (process, mods[i], modname, MAX_PATH) &&
@@ -538,7 +541,9 @@ ves_icall_System_Diagnostics_Process_GetModules_internal (MonoObject *this_obj,
                arr = temp_arr;
        } else {
                /* shorter version of the array */
-               arr = mono_array_new (mono_domain_get (), mono_class_get_process_module_class (), num_added);
+               arr = mono_array_new_checked (mono_domain_get (), mono_class_get_process_module_class (), num_added, &error);
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
 
                for (i = 0; i < num_added; i++)
                        mono_array_setref (arr, i, mono_array_get (temp_arr, MonoObject*, i));
@@ -849,6 +854,7 @@ MonoArray *
 ves_icall_System_Diagnostics_Process_GetProcesses_internal (void)
 {
 #if !defined(HOST_WIN32)
+       MonoError error;
        MonoArray *procs;
        gpointer *pidarray;
        int i, count;
@@ -858,7 +864,11 @@ ves_icall_System_Diagnostics_Process_GetProcesses_internal (void)
                mono_set_pending_exception (mono_get_exception_not_supported ("This system does not support EnumProcesses"));
                return NULL;
        }
-       procs = mono_array_new (mono_domain_get (), mono_get_int32_class (), count);
+       procs = mono_array_new_checked (mono_domain_get (), mono_get_int32_class (), count, &error);
+       if (mono_error_set_pending_exception (&error)) {
+               g_free (pidarray);
+               return NULL;
+       }
        if (sizeof (guint32) == sizeof (gpointer)) {
                memcpy (mono_array_addr (procs, guint32, 0), pidarray, count * sizeof (gint32));
        } else {
@@ -869,6 +879,7 @@ ves_icall_System_Diagnostics_Process_GetProcesses_internal (void)
 
        return procs;
 #else
+       MonoError error;
        MonoArray *procs;
        gboolean ret;
        DWORD needed;
@@ -896,7 +907,12 @@ ves_icall_System_Diagnostics_Process_GetProcesses_internal (void)
        } while (TRUE);
 
        count = needed / sizeof (guint32);
-       procs = mono_array_new (mono_domain_get (), mono_get_int32_class (), count);
+       procs = mono_array_new_checked (mono_domain_get (), mono_get_int32_class (), count, &error);
+       if (mono_error_set_pending_exception (&error)) {
+               g_free (pids);
+               return NULL;
+       }
+
        memcpy (mono_array_addr (procs, guint32, 0), pids, needed);
        g_free (pids);
        pids = NULL;
index cdd11fda385f3b6a2b0a87469d2f955b067f5bed..4920694b731f928265424c78bfa730b5238bd7aa 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com).
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -23,6 +24,7 @@
 #include "mono/metadata/mono-config-dirs.h"
 #include "mono/io-layer/io-layer.h"
 #include "mono/utils/mono-dl.h"
+#include <mono/utils/mono-logger-internals.h>
 #include <string.h>
 #ifdef HAVE_UNISTD_H
 #include <unistd.h>
@@ -281,7 +283,7 @@ mono_profiler_install_monitor  (MonoProfileMonitorFunc callback)
 }
 
 static MonoProfileSamplingMode sampling_mode = MONO_PROFILER_STAT_MODE_PROCESS;
-static int64_t sampling_frequency = 1000; //1ms
+static int64_t sampling_frequency = 100; // Hz
 
 /**
  * mono_profiler_set_statistical_mode:
@@ -296,10 +298,10 @@ static int64_t sampling_frequency = 1000; //1ms
  * Said that, when using statistical sampling, always assume variable rate sampling as all sort of external factors can interfere.
  */
 void
-mono_profiler_set_statistical_mode (MonoProfileSamplingMode mode, int64_t sampling_frequency_is_us)
+mono_profiler_set_statistical_mode (MonoProfileSamplingMode mode, int64_t sampling_frequency_hz)
 {
        sampling_mode = mode;
-       sampling_frequency = sampling_frequency_is_us;
+       sampling_frequency = sampling_frequency_hz;
 }
 
 void 
@@ -1145,7 +1147,15 @@ load_embedded_profiler (const char *desc, const char *name)
        MonoDl *pmodule = NULL;
        gboolean result;
 
-       pmodule = mono_dl_open (NULL, MONO_DL_LAZY, &err);
+       /*
+        * Some profilers (such as ours) may need to call back into the runtime
+        * from their sampling callback (which is called in async-signal context).
+        * They need to be able to know that all references back to the runtime
+        * have been resolved; otherwise, calling runtime functions may result in
+        * invoking the dynamic linker which is not async-signal-safe. Passing
+        * MONO_DL_EAGER will ask the dynamic linker to resolve everything upfront.
+        */
+       pmodule = mono_dl_open (NULL, MONO_DL_EAGER, &err);
        if (!pmodule) {
                g_warning ("Could not open main executable (%s)", err);
                g_free (err);
@@ -1159,6 +1169,7 @@ load_embedded_profiler (const char *desc, const char *name)
        return result;
 }
 
+// TODO: Much of the library loading code here is custom. It would be better to merge this with mono-dl
 static gboolean
 load_profiler_from_directory (const char *directory, const char *libname, const char *desc)
 {
@@ -1167,10 +1178,13 @@ load_profiler_from_directory (const char *directory, const char *libname, const
        char *err;
        void *iter;
 
+       mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_DLLIMPORT, "Attempting to load profiler %s from %s (desc %s)", libname, directory, desc);
+
        iter = NULL;
        err = NULL;
        while ((path = mono_dl_build_path (directory, libname, &iter))) {
-               pmodule = mono_dl_open (path, MONO_DL_LAZY, &err);
+               pmodule = mono_dl_open (path, MONO_DL_EAGER, &err);
+               mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_DLLIMPORT, "Attempting to load profiler: %s, %ssuccessful, err: %s", path, pmodule?"":"not ", err);
                g_free (path);
                g_free (err);
                if (pmodule)
@@ -1181,10 +1195,11 @@ load_profiler_from_directory (const char *directory, const char *libname, const
 }
 
 static gboolean
-load_profiler_from_mono_instalation (const char *libname, const char *desc)
+load_profiler_from_mono_installation (const char *libname, const char *desc)
 {
        char *err = NULL;
-       MonoDl *pmodule = mono_dl_open_runtime_lib (libname, MONO_DL_LAZY, &err);
+       MonoDl *pmodule = mono_dl_open_runtime_lib (libname, MONO_DL_EAGER, &err);
+       mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_DLLIMPORT, "Attempting to load profiler from runtime libs: %s, %ssuccessful, err: %s", libname, pmodule?"":"not ", err);
        g_free (err);
        if (pmodule)
                return load_profiler (pmodule, desc, INITIALIZER_NAME);
@@ -1249,12 +1264,11 @@ mono_profiler_load (const char *desc)
                }
                if (!load_embedded_profiler (desc, mname)) {
                        libname = g_strdup_printf ("mono-profiler-%s", mname);
-                       if (mono_config_get_assemblies_dir ())
+                       res = load_profiler_from_mono_installation (libname, desc);
+                       if (!res && mono_config_get_assemblies_dir ())
                                res = load_profiler_from_directory (mono_assembly_getrootdir (), libname, desc);
                        if (!res)
                                res = load_profiler_from_directory (NULL, libname, desc);
-                       if (!res)
-                               res = load_profiler_from_mono_instalation (libname, desc);
                        if (!res)
                                g_warning ("The '%s' profiler wasn't found in the main executable nor could it be loaded from '%s'.", mname, libname);
                        g_free (libname);
index 17128a1cb5a79d950d70cc90c6a73337fae24b0b..b793548ef8fbd98782f7975b1b08ffd0d0a3634d 100644 (file)
@@ -214,7 +214,7 @@ typedef enum {
        MONO_PROFILER_STAT_MODE_REAL = 1,
 } MonoProfileSamplingMode;
 
-MONO_API void mono_profiler_set_statistical_mode (MonoProfileSamplingMode mode, int64_t sampling_frequency_is_us);
+MONO_API void mono_profiler_set_statistical_mode (MonoProfileSamplingMode mode, int64_t sampling_frequency_hz);
 
 MONO_END_DECLS
 
index 422bda1d1bc991994ec5012c02c00a1ddeae4580..87d2d104790dceb6272299c34f19911ceb362615 100644 (file)
@@ -8,6 +8,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <glib.h>
index 15af782fdc65b1b86409c61c56a9c401cc47126b..563b374835969d1375f8562b19057528e8bb4860 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2001 Ximian, Inc.
  * Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_RAND_H_
index af5ba0afdb0b0a6420e1f309712fb928d04cf811..327bb93142ce85d0579bf1bd8ae484a92e545331 100644 (file)
@@ -1,5 +1,6 @@
 /* 
  * Copyright 2014 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_METADATA_REFLECTION_INTERNALS_H__
 #define __MONO_METADATA_REFLECTION_INTERNALS_H__
@@ -9,7 +10,7 @@
 #include <mono/utils/mono-error.h>
 
 MonoType*
-mono_reflection_get_type_checked (MonoImage* image, MonoTypeNameParse *info, mono_bool ignorecase, mono_bool *type_resolve, MonoError *error);
+mono_reflection_get_type_checked (MonoImage *rootimage, MonoImage* image, MonoTypeNameParse *info, mono_bool ignorecase, mono_bool *type_resolve, MonoError *error);
 
 MonoType*
 mono_reflection_type_from_name_checked (char *name, MonoImage *image, MonoError *error);
@@ -27,6 +28,9 @@ mono_reflection_get_custom_attrs_info_checked (MonoObject *obj, MonoError *error
 MonoArray*
 mono_reflection_get_custom_attrs_data_checked (MonoObject *obj, MonoError *error);
 
+MonoArray*
+mono_reflection_get_custom_attrs_blob_checked (MonoReflectionAssembly *assembly, MonoObject *ctor, MonoArray *ctorArgs, MonoArray *properties, MonoArray *propValues, MonoArray *fields, MonoArray* fieldValues, MonoError *error);
+
 MonoCustomAttrInfo*
 mono_custom_attrs_from_index_checked    (MonoImage *image, uint32_t idx, MonoError *error);
 MonoCustomAttrInfo*
index a3ea522b1cf5e1cccdccde76bbd134070ae6fe9f..5488e7df3d8432c5e3e05ba91dd931624867290d 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Rodrigo Kumpera
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include "mono/utils/mono-digest.h"
@@ -151,7 +152,7 @@ static guint32 mono_image_get_methodbuilder_token (MonoDynamicImage *assembly, M
 static guint32 mono_image_get_ctorbuilder_token (MonoDynamicImage *assembly, MonoReflectionCtorBuilder *cb, MonoError *error);
 static guint32 mono_image_get_sighelper_token (MonoDynamicImage *assembly, MonoReflectionSigHelper *helper, MonoError *error);
 static gboolean ensure_runtime_vtable (MonoClass *klass, MonoError  *error);
-static gpointer resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, MonoGenericContext *context);
+static gpointer resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, MonoGenericContext *context, MonoError *error);
 static guint32 mono_image_get_methodref_token_for_methodbuilder (MonoDynamicImage *assembly, MonoReflectionMethodBuilder *method, MonoError *error);
 static guint32 encode_generic_method_sig (MonoDynamicImage *assembly, MonoGenericContext *context);
 static gpointer register_assembly (MonoDomain *domain, MonoReflectionAssembly *res, MonoAssembly *assembly);
@@ -187,12 +188,14 @@ static gboolean is_sr_mono_property (MonoClass *klass);
 static gboolean is_sre_method_on_tb_inst (MonoClass *klass);
 static gboolean is_sre_ctor_on_tb_inst (MonoClass *klass);
 
+static gboolean type_is_reference (MonoType *type);
+
 static guint32 mono_image_get_methodspec_token (MonoDynamicImage *assembly, MonoMethod *method);
 static guint32 mono_image_get_inflated_method_token (MonoDynamicImage *assembly, MonoMethod *m);
 static MonoMethod * inflate_method (MonoReflectionType *type, MonoObject *obj, MonoError *error);
 
 static guint32 create_typespec (MonoDynamicImage *assembly, MonoType *type);
-static void init_type_builder_generics (MonoObject *type);
+static void init_type_builder_generics (MonoObject *type, MonoError *error);
 
 #define RESOLVE_TYPE(type, error) do {                                 \
        type = (MonoObject *)mono_reflection_type_resolve_user_types ((MonoReflectionType*)type, error); \
@@ -2059,7 +2062,8 @@ field_encode_signature (MonoDynamicImage *assembly, MonoReflectionFieldBuilder *
        MonoType *type;
        MonoClass *klass;
 
-       init_type_builder_generics (fb->type);
+       init_type_builder_generics (fb->type, error);
+       return_val_if_nok (error, 0);
 
        type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
        return_val_if_nok (error, 0);
@@ -3315,7 +3319,8 @@ mono_reflection_method_on_tb_inst_get_handle (MonoReflectionMethodOnTypeBuilderI
 
        mono_error_init (error);
 
-       init_type_builder_generics ((MonoObject*)m->inst);
+       init_type_builder_generics ((MonoObject*)m->inst, error);
+       return_val_if_nok (error, NULL);
 
        method = inflate_method (m->inst, (MonoObject*)m->mb, error);
        return_val_if_nok (error, NULL);
@@ -3552,8 +3557,10 @@ create_generic_typespec (MonoDynamicImage *assembly, MonoReflectionTypeBuilder *
        g_assert (tb->generic_params);
        klass = mono_class_from_mono_type (type);
 
-       if (tb->generic_container)
-               mono_reflection_create_generic_class (tb);
+       if (tb->generic_container) {
+               if (!mono_reflection_create_generic_class (tb, error))
+                       goto fail;
+       }
 
        sigbuffer_add_value (&buf, MONO_TYPE_GENERICINST);
        g_assert (klass->generic_container);
@@ -3646,16 +3653,18 @@ fail:
 }
 
 static void
-init_type_builder_generics (MonoObject *type)
+init_type_builder_generics (MonoObject *type, MonoError *error)
 {
        MonoReflectionTypeBuilder *tb;
 
+       mono_error_init (error);
+
        if (!is_sre_type_builder(mono_object_class (type)))
                return;
        tb = (MonoReflectionTypeBuilder *)type;
 
        if (tb && tb->generic_container)
-               mono_reflection_create_generic_class (tb);
+               mono_reflection_create_generic_class (tb, error);
 }
 
 static guint32
@@ -3679,7 +3688,8 @@ mono_image_get_generic_field_token (MonoDynamicImage *assembly, MonoReflectionFi
        mono_class_from_mono_type (typeb);
 
        /*FIXME this is one more layer of ugliness due how types are created.*/
-       init_type_builder_generics (fb->type);
+       init_type_builder_generics (fb->type, error);
+       return_val_if_nok (error, 0);
 
        /* fb->type does not include the custom modifiers */
        /* FIXME: We should do this in one place when a fieldbuilder is created */
@@ -5533,7 +5543,7 @@ mono_image_create_token (MonoDynamicImage *assembly, MonoObject *obj,
        /* Check for user defined reflection objects */
        /* TypeDelegator is the only corlib type which doesn't look like a MonoReflectionType */
        if (klass->image != mono_defaults.corlib || (strcmp (klass->name, "TypeDelegator") == 0)) {
-               mono_error_set_generic_error (error, "System", "NotSupportedException", "User defined subclasses of System.Type are not yet supported");
+               mono_error_set_not_supported (error, "User defined subclasses of System.Type are not yet supported");
                return 0;
        }
 
@@ -5578,7 +5588,8 @@ mono_image_create_token (MonoDynamicImage *assembly, MonoObject *obj,
                MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder *)obj;
                if (create_open_instance && tb->generic_params) {
                        MonoType *type;
-                       init_type_builder_generics (obj);
+                       init_type_builder_generics (obj, error);
+                       return_val_if_nok (error, 0);
                        type = mono_reflection_type_get_handle ((MonoReflectionType *)obj, error);
                        return_val_if_nok (error, 0);
                        token = mono_image_typedef_or_ref_full (assembly, type, TRUE);
@@ -6851,13 +6862,13 @@ register_module (MonoDomain *domain, MonoReflectionModuleBuilder *res, MonoDynam
        CACHE_OBJECT (MonoReflectionModuleBuilder *, module, res, NULL);
 }
 
-void
-mono_image_module_basic_init (MonoReflectionModuleBuilder *moduleb)
+static gboolean
+image_module_basic_init (MonoReflectionModuleBuilder *moduleb, MonoError *error)
 {
        MonoDynamicImage *image = moduleb->dynamic_image;
        MonoReflectionAssemblyBuilder *ab = moduleb->assemblyb;
+       mono_error_init (error);
        if (!image) {
-               MonoError error;
                int module_count;
                MonoImage **new_modules;
                MonoImage *ass;
@@ -6869,10 +6880,10 @@ mono_image_module_basic_init (MonoReflectionModuleBuilder *moduleb)
                 */
                /*image = (MonoDynamicImage*)ab->dynamic_assembly->assembly.image; */
                name = mono_string_to_utf8 (ab->name);
-               fqname = mono_string_to_utf8_checked (moduleb->module.fqname, &error);
-               if (!mono_error_ok (&error)) {
+               fqname = mono_string_to_utf8_checked (moduleb->module.fqname, error);
+               if (!is_ok (error)) {
                        g_free (name);
-                       mono_error_raise_exception (&error);
+                       return FALSE;
                }
                image = create_dynamic_mono_image (ab->dynamic_assembly, name, fqname);
 
@@ -6894,6 +6905,15 @@ mono_image_module_basic_init (MonoReflectionModuleBuilder *moduleb)
                ass->modules = new_modules;
                ass->module_count ++;
        }
+       return TRUE;
+}
+
+void
+mono_image_module_basic_init (MonoReflectionModuleBuilder *moduleb)
+{
+       MonoError error;
+       (void) image_module_basic_init (moduleb, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 void
@@ -6954,7 +6974,7 @@ mono_module_get_object   (MonoDomain *domain, MonoImage *image)
        MonoError error;
        MonoReflectionModule *result;
        result = mono_module_get_object_checked (domain, image, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7006,7 +7026,7 @@ mono_module_file_get_object (MonoDomain *domain, MonoImage *image, int table_ind
        MonoError error;
        MonoReflectionModule *result;
        result = mono_module_file_get_object_checked (domain, image, table_index, &error);
-       mono_error_cleanup (&error); /* FIXME new API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7140,7 +7160,7 @@ mono_type_get_object (MonoDomain *domain, MonoType *type)
 {
        MonoError error;
        MonoReflectionType *ret = mono_type_get_object_checked (domain, type, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
 
        return ret;
 }
@@ -7278,7 +7298,7 @@ mono_method_get_object (MonoDomain *domain, MonoMethod *method, MonoClass *refcl
        MonoError error;
        MonoReflectionMethod *ret = NULL;
        ret = mono_method_get_object_checked (domain, method, refclass, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return ret;
 }
 
@@ -7400,7 +7420,7 @@ mono_field_get_object (MonoDomain *domain, MonoClass *klass, MonoClassField *fie
        MonoError error;
        MonoReflectionField *result;
        result = mono_field_get_object_checked (domain, klass, field, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7466,7 +7486,7 @@ mono_property_get_object (MonoDomain *domain, MonoClass *klass, MonoProperty *pr
        MonoError error;
        MonoReflectionProperty *result;
        result = mono_property_get_object_checked (domain, klass, property, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7511,7 +7531,7 @@ mono_event_get_object (MonoDomain *domain, MonoClass *klass, MonoEvent *event)
        MonoError error;
        MonoReflectionEvent *result;
        result = mono_event_get_object_checked (domain, klass, event, &error);
-       mono_error_raise_exception (&error);
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7773,7 +7793,7 @@ mono_method_body_get_object (MonoDomain *domain, MonoMethod *method)
 {
        MonoError error;
        MonoReflectionMethodBody *result = mono_method_body_get_object_checked (domain, method, &error);
-       mono_error_cleanup (&error); /* FIXME new API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -7802,7 +7822,7 @@ mono_method_body_get_object_checked (MonoDomain *domain, MonoMethod *method, Mon
 
        /* for compatibility with .net */
        if (method_is_dynamic (method)) {
-               mono_error_set_exception_instance (error, mono_get_exception_invalid_operation (NULL));
+               mono_error_set_generic_error (error, "System", "InvalidOperationException", "");
                return NULL;
        }
 
@@ -7842,22 +7862,31 @@ mono_method_body_get_object_checked (MonoDomain *domain, MonoMethod *method, Mon
                local_var_sig_token = 0; //FIXME
 
        ret = (MonoReflectionMethodBody*)mono_object_new_checked (domain, mono_class_get_method_body_class (), error);
-       return_val_if_nok (error, NULL);
+       if (!is_ok (error))
+               goto fail;
 
        ret->init_locals = header->init_locals;
        ret->max_stack = header->max_stack;
        ret->local_var_sig_token = local_var_sig_token;
-       MONO_OBJECT_SETREF (ret, il, mono_array_new_cached (domain, mono_defaults.byte_class, header->code_size));
+       MonoArray *il_arr = mono_array_new_cached (domain, mono_defaults.byte_class, header->code_size, error);
+       if (!is_ok (error))
+               goto fail;
+       MONO_OBJECT_SETREF (ret, il, il_arr);
        memcpy (mono_array_addr (ret->il, guint8, 0), header->code, header->code_size);
 
        /* Locals */
-       MONO_OBJECT_SETREF (ret, locals, mono_array_new_cached (domain, mono_class_get_local_variable_info_class (), header->num_locals));
+       MonoArray *locals_arr = mono_array_new_cached (domain, mono_class_get_local_variable_info_class (), header->num_locals, error);
+       if (!is_ok (error))
+               goto fail;
+       MONO_OBJECT_SETREF (ret, locals, locals_arr);
        for (i = 0; i < header->num_locals; ++i) {
                MonoReflectionLocalVariableInfo *info = (MonoReflectionLocalVariableInfo*)mono_object_new_checked (domain, mono_class_get_local_variable_info_class (), error);
-               return_val_if_nok (error, NULL);
+               if (!is_ok (error))
+                       goto fail;
 
                rt = mono_type_get_object_checked (domain, header->locals [i], error);
-               return_val_if_nok (error, NULL);
+               if (!is_ok (error))
+                       goto fail;
 
                MONO_OBJECT_SETREF (info, local_type, rt);
 
@@ -7867,10 +7896,14 @@ mono_method_body_get_object_checked (MonoDomain *domain, MonoMethod *method, Mon
        }
 
        /* Exceptions */
-       MONO_OBJECT_SETREF (ret, clauses, mono_array_new_cached (domain, mono_class_get_exception_handling_clause_class (), header->num_clauses));
+       MonoArray *exn_clauses = mono_array_new_cached (domain, mono_class_get_exception_handling_clause_class (), header->num_clauses, error);
+       if (!is_ok (error))
+               goto fail;
+       MONO_OBJECT_SETREF (ret, clauses, exn_clauses);
        for (i = 0; i < header->num_clauses; ++i) {
                MonoReflectionExceptionHandlingClause *info = (MonoReflectionExceptionHandlingClause*)mono_object_new_checked (domain, mono_class_get_exception_handling_clause_class (), error);
-               return_val_if_nok (error, NULL);
+               if (!is_ok (error))
+                       goto fail;
                MonoExceptionClause *clause = &header->clauses [i];
 
                info->flags = clause->flags;
@@ -7882,7 +7915,8 @@ mono_method_body_get_object_checked (MonoDomain *domain, MonoMethod *method, Mon
                        info->filter_offset = clause->data.filter_offset;
                else if (clause->data.catch_class) {
                        rt = mono_type_get_object_checked (mono_domain_get (), &clause->data.catch_class->byval_arg, error);
-                       return_val_if_nok (error, NULL);
+                       if (!is_ok (error))
+                               goto fail;
 
                        MONO_OBJECT_SETREF (info, catch_type, rt);
                }
@@ -7893,6 +7927,10 @@ mono_method_body_get_object_checked (MonoDomain *domain, MonoMethod *method, Mon
        mono_metadata_free_mh (header);
        CACHE_OBJECT (MonoReflectionMethodBody *, method, ret, NULL);
        return ret;
+
+fail:
+       mono_metadata_free_mh (header);
+       return NULL;
 }
 
 /**
@@ -8571,7 +8609,7 @@ mono_reflection_get_type_internal (MonoImage *rootimage, MonoImage* image, MonoT
                        return NULL;
 
                instance = mono_reflection_bind_generic_parameters (
-                       the_type, info->type_arguments->len, type_args);
+                       the_type, info->type_arguments->len, type_args, error);
 
                g_free (type_args);
                if (!instance)
@@ -8617,6 +8655,7 @@ mono_reflection_get_type (MonoImage* image, MonoTypeNameParse *info, gboolean ig
 
 /**
  * mono_reflection_get_type_checked:
+ * @rootimage: the image of the currently active managed caller
  * @image: a metadata context
  * @info: type description structure
  * @ignorecase: flag for case-insensitive string compares
@@ -8627,9 +8666,9 @@ mono_reflection_get_type (MonoImage* image, MonoTypeNameParse *info, gboolean ig
  *
  */
 MonoType*
-mono_reflection_get_type_checked (MonoImage* image, MonoTypeNameParse *info, gboolean ignorecase, gboolean *type_resolve, MonoError *error) {
+mono_reflection_get_type_checked (MonoImage *rootimage, MonoImage* image, MonoTypeNameParse *info, gboolean ignorecase, gboolean *type_resolve, MonoError *error) {
        mono_error_init (error);
-       return mono_reflection_get_type_with_rootimage (image, image, info, ignorecase, type_resolve, error);
+       return mono_reflection_get_type_with_rootimage (rootimage, image, info, ignorecase, type_resolve, error);
 }
 
 
@@ -8914,8 +8953,8 @@ mono_reflection_get_token_checked (MonoObject *obj, MonoError *error)
        } else if (strcmp (klass->name, "Assembly") == 0 || strcmp (klass->name, "MonoAssembly") == 0) {
                token = mono_metadata_make_token (MONO_TABLE_ASSEMBLY, 1);
        } else {
-               mono_error_set_generic_error (error, "System", "NotImplementedException",
-                                             "MetadataToken is not supported for type '%s.%s'", klass->name_space, klass->name);
+               mono_error_set_not_implemented (error, "MetadataToken is not supported for type '%s.%s'",
+                                               klass->name_space, klass->name);
                return 0;
        }
 
@@ -9027,7 +9066,7 @@ handle_enum:
                }
                slen = mono_metadata_decode_value (p, &p);
                *end = p + slen;
-               return mono_string_new_len (mono_domain_get (), p, slen);
+               return mono_string_new_len_checked (mono_domain_get (), p, slen, error);
        case MONO_TYPE_CLASS: {
                MonoReflectionType *rt;
                char *n;
@@ -9135,7 +9174,8 @@ handle_type:
                        *end = p;
                        return NULL;
                }
-               arr = mono_array_new (mono_domain_get(), tklass, alen);
+               arr = mono_array_new_checked (mono_domain_get(), tklass, alen, error);
+               return_val_if_nok (error, NULL);
                basetype = tklass->byval_arg.type;
                if (basetype == MONO_TYPE_VALUETYPE && tklass->enumtype)
                        basetype = mono_class_enum_basetype (tklass)->type;
@@ -9206,6 +9246,28 @@ handle_type:
        return NULL;
 }
 
+static MonoObject*
+load_cattr_value_boxed (MonoDomain *domain, MonoImage *image, MonoType *t, const char* p, const char** end, MonoError *error)
+{
+       mono_error_init (error);
+
+       gboolean is_ref = type_is_reference (t);
+
+       void *val = load_cattr_value (image, t, p, end, error);
+       if (!is_ok (error)) {
+               if (is_ref)
+                       g_free (val);
+               return NULL;
+       }
+
+       if (is_ref)
+               return (MonoObject*)val;
+
+       MonoObject *boxed = mono_value_box_checked (domain, mono_class_from_mono_type (t), val, error);
+       g_free (val);
+       return boxed;
+}
+
 static MonoObject*
 create_cattr_typed_arg (MonoType *t, MonoObject *val, MonoError *error)
 {
@@ -9343,7 +9405,6 @@ create_custom_attr (MonoImage *image, MonoMethod *method, const guchar *data, gu
        void *params_buf [32];
        void **params = NULL;
        MonoMethodSignature *sig;
-       MonoObject *exc = NULL;
 
        mono_error_init (error);
 
@@ -9391,11 +9452,14 @@ create_custom_attr (MonoImage *image, MonoMethod *method, const guchar *data, gu
        attr = mono_object_new_checked (mono_domain_get (), method->klass, error);
        if (!mono_error_ok (error)) goto fail;
 
+       MonoObject *exc = NULL;
        mono_runtime_try_invoke (method, attr, params, &exc, error);
        if (!mono_error_ok (error))
                goto fail;
-       if (exc)
+       if (exc) {
+               mono_error_set_exception_instance (error, (MonoException*)exc);
                goto fail;
+       }
 
        num_named = read16 (named);
        named += 2;
@@ -9477,9 +9541,13 @@ create_custom_attr (MonoImage *image, MonoMethod *method, const guchar *data, gu
                        }
 
 
-                       mono_property_set_value (prop, attr, pparams, NULL);
+                       mono_property_set_value_checked (prop, attr, pparams, error);
                        if (!type_is_reference (prop_type))
                                g_free (pparams [0]);
+                       if (!is_ok (error)) {
+                               g_free (name);
+                               goto fail;
+                       }
                }
                g_free (name);
        }
@@ -9494,8 +9562,6 @@ fail:
        free_param_data (method->signature, params);
        if (params != params_buf)
                mono_gc_free_fixed (params);
-       if (exc)
-               mono_raise_exception ((MonoException*)exc);
        return NULL;
 }
        
@@ -9535,32 +9601,23 @@ mono_reflection_create_custom_attr_data_args (MonoImage *image, MonoMethod *meth
        if (len < 2 || read16 (p) != 0x0001) /* Prolog */
                return;
 
-       typedargs = mono_array_new (domain, mono_get_object_class (), mono_method_signature (method)->param_count);
-       
+       typedargs = mono_array_new_checked (domain, mono_get_object_class (), mono_method_signature (method)->param_count, error);
+       return_if_nok (error);
+
        /* skip prolog */
        p += 2;
        for (i = 0; i < mono_method_signature (method)->param_count; ++i) {
                MonoObject *obj;
-               void *val;
-
-               val = load_cattr_value (image, mono_method_signature (method)->params [i], p, &p, error);
-               if (!mono_error_ok (error)) {
-                       if (!type_is_reference (mono_method_signature (method)->params [i]))
-                               g_free (val);
-                       return;
-               }
 
-               obj = (MonoObject *)(type_is_reference (mono_method_signature (method)->params [i]) ?
-                       val : mono_value_box (domain, mono_class_from_mono_type (mono_method_signature (method)->params [i]), val));
+               obj = load_cattr_value_boxed (domain, image, mono_method_signature (method)->params [i], p, &p, error);
+               return_if_nok (error);
                mono_array_setref (typedargs, i, obj);
-
-               if (!type_is_reference (mono_method_signature (method)->params [i]))
-                       g_free (val);
        }
 
        named = p;
        num_named = read16 (named);
-       namedargs = mono_array_new (domain, mono_get_object_class (), num_named);
+       namedargs = mono_array_new_checked (domain, mono_get_object_class (), num_named, error);
+       return_if_nok (error);
        named += 2;
        attrklass = method->klass;
 
@@ -9598,7 +9655,6 @@ mono_reflection_create_custom_attr_data_args (MonoImage *image, MonoMethod *meth
                if (named_type == 0x53) {
                        MonoObject *obj;
                        MonoClassField *field = mono_class_get_field_from_name (attrklass, name);
-                       void *val;
 
                        if (!field) {
                                g_free (name);
@@ -9608,23 +9664,17 @@ mono_reflection_create_custom_attr_data_args (MonoImage *image, MonoMethod *meth
                        arginfo [j].type = field->type;
                        arginfo [j].field = field;
 
-                       val = load_cattr_value (image, field->type, named, &named, error);
-                       if (!mono_error_ok (error)) {
-                               if (!type_is_reference (field->type))
-                                       g_free (val);
+                       obj = load_cattr_value_boxed (domain, image, field->type, named, &named, error);
+                       if (!is_ok (error)) {
                                g_free (name);
                                return;
                        }
-
-                       obj = (MonoObject *)(type_is_reference (field->type) ? val : mono_value_box (domain, mono_class_from_mono_type (field->type), val));
                        mono_array_setref (namedargs, j, obj);
-                       if (!type_is_reference (field->type))
-                               g_free (val);
+
                } else if (named_type == 0x54) {
                        MonoObject *obj;
                        MonoType *prop_type;
                        MonoProperty *prop = mono_class_get_property_from_name (attrklass, name);
-                       void *val;
 
                        if (!prop || !prop->set) {
                                g_free (name);
@@ -9637,18 +9687,12 @@ mono_reflection_create_custom_attr_data_args (MonoImage *image, MonoMethod *meth
                        arginfo [j].type = prop_type;
                        arginfo [j].prop = prop;
 
-                       val = load_cattr_value (image, prop_type, named, &named, error);
-                       if (!mono_error_ok (error)) {
-                               if (!type_is_reference (prop_type))
-                                       g_free (val);
+                       obj = load_cattr_value_boxed (domain, image, prop_type, named, &named, error);
+                       if (!is_ok (error)) {
                                g_free (name);
                                return;
                        }
-
-                       obj = (MonoObject *)(type_is_reference (prop_type) ? val : mono_value_box (domain, mono_class_from_mono_type (prop_type), val));
                        mono_array_setref (namedargs, j, obj);
-                       if (!type_is_reference (prop_type))
-                               g_free (val);
                }
                g_free (name);
        }
@@ -9662,40 +9706,36 @@ fail:
        *named_arg_info = NULL;
 }
 
-void
-mono_reflection_resolve_custom_attribute_data (MonoReflectionMethod *ref_method, MonoReflectionAssembly *assembly, gpointer data, guint32 len, MonoArray **ctor_args, MonoArray **named_args)
+static gboolean
+reflection_resolve_custom_attribute_data (MonoReflectionMethod *ref_method, MonoReflectionAssembly *assembly, gpointer data, guint32 len, MonoArray **ctor_args, MonoArray **named_args, MonoError *error)
 {
        MonoDomain *domain;
        MonoArray *typedargs, *namedargs;
        MonoImage *image;
        MonoMethod *method;
        CattrNamedArg *arginfo = NULL;
-       MonoError error;
        int i;
 
-       mono_error_init (&error);
+       mono_error_init (error);
 
        *ctor_args = NULL;
        *named_args = NULL;
 
        if (len == 0)
-               return;
+               return TRUE;
 
        image = assembly->assembly->image;
        method = ref_method->method;
        domain = mono_object_domain (ref_method);
 
-       if (!mono_class_init (method->klass))
-               mono_raise_exception (mono_class_get_exception_for_failure (method->klass));
-
-       mono_reflection_create_custom_attr_data_args (image, method, (const guchar *)data, len, &typedargs, &namedargs, &arginfo, &error);
-       if (!mono_error_ok (&error))
+       if (!mono_class_init (method->klass)) {
+               mono_error_set_exception_instance (error, mono_class_get_exception_for_failure (method->klass));
                goto leave;
+       }
 
-       if (mono_loader_get_last_error ()) {
-               mono_error_set_from_loader_error (&error);
+       mono_reflection_create_custom_attr_data_args (image, method, (const guchar *)data, len, &typedargs, &namedargs, &arginfo, error);
+       if (!is_ok (error))
                goto leave;
-       }
 
        if (!typedargs || !namedargs)
                goto leave;
@@ -9704,8 +9744,8 @@ mono_reflection_resolve_custom_attribute_data (MonoReflectionMethod *ref_method,
                MonoObject *obj = mono_array_get (typedargs, MonoObject*, i);
                MonoObject *typedarg;
 
-               typedarg = create_cattr_typed_arg (mono_method_signature (method)->params [i], obj, &error);
-               if (!is_ok (&error))
+               typedarg = create_cattr_typed_arg (mono_method_signature (method)->params [i], obj, error);
+               if (!is_ok (error))
                        goto leave;
                mono_array_setref (typedargs, i, typedarg);
        }
@@ -9715,20 +9755,20 @@ mono_reflection_resolve_custom_attribute_data (MonoReflectionMethod *ref_method,
                MonoObject *typedarg, *namedarg, *minfo;
 
                if (arginfo [i].prop) {
-                       minfo = (MonoObject*)mono_property_get_object_checked (domain, NULL, arginfo [i].prop, &error);
+                       minfo = (MonoObject*)mono_property_get_object_checked (domain, NULL, arginfo [i].prop, error);
                        if (!minfo)
                                goto leave;
                } else {
-                       minfo = (MonoObject*)mono_field_get_object_checked (domain, NULL, arginfo [i].field, &error);
-                       if (!mono_error_ok (&error))
+                       minfo = (MonoObject*)mono_field_get_object_checked (domain, NULL, arginfo [i].field, error);
+                       if (!is_ok (error))
                                goto leave;
                }
 
-               typedarg = create_cattr_typed_arg (arginfo [i].type, obj, &error);
-               if (!is_ok (&error))
+               typedarg = create_cattr_typed_arg (arginfo [i].type, obj, error);
+               if (!is_ok (error))
                        goto leave;
-               namedarg = create_cattr_named_arg (minfo, typedarg, &error);
-               if (!is_ok (&error))
+               namedarg = create_cattr_named_arg (minfo, typedarg, error);
+               if (!is_ok (error))
                        goto leave;
 
                mono_array_setref (namedargs, i, namedarg);
@@ -9736,10 +9776,18 @@ mono_reflection_resolve_custom_attribute_data (MonoReflectionMethod *ref_method,
 
        *ctor_args = typedargs;
        *named_args = namedargs;
+
 leave:
        g_free (arginfo);
-       mono_error_raise_exception (&error);
+       return mono_error_ok (error);
+}
 
+void
+ves_icall_System_Reflection_CustomAttributeData_ResolveArgumentsInternal (MonoReflectionMethod *ref_method, MonoReflectionAssembly *assembly, gpointer data, guint32 len, MonoArray **ctor_args, MonoArray **named_args)
+{
+       MonoError error;
+       (void) reflection_resolve_custom_attribute_data (ref_method, assembly, data, len, ctor_args, named_args, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 static MonoObject*
@@ -9788,7 +9836,8 @@ mono_custom_attrs_construct_by_type (MonoCustomAttrInfo *cinfo, MonoClass *attr_
                        n ++;
        }
 
-       result = mono_array_new_cached (mono_domain_get (), mono_defaults.attribute_class, n);
+       result = mono_array_new_cached (mono_domain_get (), mono_defaults.attribute_class, n, error);
+       return_val_if_nok (error, NULL);
        n = 0;
        for (i = 0; i < cinfo->num_attrs; ++i) {
                if (!cinfo->attrs [i].ctor) {
@@ -9826,7 +9875,8 @@ mono_custom_attrs_data_construct (MonoCustomAttrInfo *cinfo, MonoError *error)
        int i;
        
        mono_error_init (error);
-       result = mono_array_new (mono_domain_get (), mono_defaults.customattribute_data_class, cinfo->num_attrs);
+       result = mono_array_new_checked (mono_domain_get (), mono_defaults.customattribute_data_class, cinfo->num_attrs, error);
+       return_val_if_nok (error, NULL);
        for (i = 0; i < cinfo->num_attrs; ++i) {
                attr = create_custom_attr_data (cinfo->image, &cinfo->attrs [i], error);
                return_val_if_nok (error, NULL);
@@ -9845,7 +9895,7 @@ mono_custom_attrs_from_index (MonoImage *image, guint32 idx)
 {
        MonoError error;
        MonoCustomAttrInfo *result = mono_custom_attrs_from_index_checked (image, idx, &error);
-       mono_error_cleanup (&error); /* FIXME a better public API that doesn't swallow the error. */
+       mono_error_cleanup (&error);
        return result;
 }
 /**
@@ -9966,7 +10016,7 @@ mono_custom_attrs_from_class (MonoClass *klass)
 {
        MonoError error;
        MonoCustomAttrInfo *result = mono_custom_attrs_from_class_checked (klass, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10000,7 +10050,7 @@ mono_custom_attrs_from_assembly (MonoAssembly *assembly)
 {
        MonoError error;
        MonoCustomAttrInfo *result = mono_custom_attrs_from_assembly_checked (assembly, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10037,7 +10087,7 @@ mono_custom_attrs_from_property (MonoClass *klass, MonoProperty *property)
 {
        MonoError error;
        MonoCustomAttrInfo * result = mono_custom_attrs_from_property_checked (klass, property, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10061,7 +10111,7 @@ mono_custom_attrs_from_event (MonoClass *klass, MonoEvent *event)
 {
        MonoError error;
        MonoCustomAttrInfo * result = mono_custom_attrs_from_event_checked (klass, event, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10085,7 +10135,7 @@ mono_custom_attrs_from_field (MonoClass *klass, MonoClassField *field)
 {
        MonoError error;
        MonoCustomAttrInfo * result = mono_custom_attrs_from_field_checked (klass, field, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10119,7 +10169,7 @@ mono_custom_attrs_from_param (MonoMethod *method, guint32 param)
 {
        MonoError error;
        MonoCustomAttrInfo *result = mono_custom_attrs_from_param_checked (method, param, &error);
-       mono_error_cleanup (&error); /* FIXME want a better API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10219,7 +10269,7 @@ mono_custom_attrs_get_attr (MonoCustomAttrInfo *ainfo, MonoClass *attr_klass)
 {
        MonoError error;
        MonoObject *res = mono_custom_attrs_get_attr_checked (ainfo, attr_klass, &error);
-       g_assert (mono_error_ok (&error)); /*FIXME proper error handling*/
+       mono_error_assert_ok (&error); /*FIXME proper error handling*/
        return res;
 }
 
@@ -10362,7 +10412,7 @@ mono_reflection_get_custom_attrs_info_checked (MonoObject *obj, MonoError *error
 #endif
                else {
                        char *type_name = mono_type_get_full_name (member_class);
-                       mono_error_set_generic_error (error, "System", "NotSupportedException",
+                       mono_error_set_not_supported (error,
                                                      "Custom attributes on a ParamInfo with member %s are not supported",
                                                      type_name);
                        g_free (type_name);
@@ -10418,13 +10468,12 @@ mono_reflection_get_custom_attrs_by_type (MonoObject *obj, MonoClass *attr_klass
        return_val_if_nok (error, NULL);
        if (cinfo) {
                result = mono_custom_attrs_construct_by_type (cinfo, attr_klass, error);
-               if (!result)
-                       return NULL;
                if (!cinfo->cached)
                        mono_custom_attrs_free (cinfo);
+               if (!result)
+                       return NULL;
        } else {
-               mono_loader_assert_no_error ();
-               result = mono_array_new_cached (mono_domain_get (), mono_defaults.attribute_class, 0);
+               result = mono_array_new_cached (mono_domain_get (), mono_defaults.attribute_class, 0, error);
        }
 
        return result;
@@ -10460,7 +10509,7 @@ mono_reflection_get_custom_attrs_data (MonoObject *obj)
        MonoError error;
        MonoArray* result;
        result = mono_reflection_get_custom_attrs_data_checked (obj, &error);
-       mono_error_cleanup (&error); /* FIXME new API that doesn't swallow the error */
+       mono_error_cleanup (&error);
        return result;
 }
 
@@ -10485,14 +10534,11 @@ mono_reflection_get_custom_attrs_data_checked (MonoObject *obj, MonoError *error
        return_val_if_nok (error, NULL);
        if (cinfo) {
                result = mono_custom_attrs_data_construct (cinfo, error);
-               return_val_if_nok (error, NULL);
                if (!cinfo->cached)
                        mono_custom_attrs_free (cinfo);
-       } else
-               result = mono_array_new (mono_domain_get (), mono_defaults.customattribute_data_class, 0);
-
-       if (mono_loader_get_last_error ())
-               mono_error_set_from_loader_error (error);
+               return_val_if_nok (error, NULL);
+       } else 
+               result = mono_array_new_checked (mono_domain_get (), mono_defaults.customattribute_data_class, 0, error);
 
        return result;
 }
@@ -10663,7 +10709,7 @@ mono_reflection_type_get_handle (MonoReflectionType* ref, MonoError *error)
                        }
                }
 
-               res = mono_reflection_bind_generic_parameters (gclass->generic_type, count, types);
+               res = mono_reflection_bind_generic_parameters (gclass->generic_type, count, types, error);
                g_free (types);
                g_assert (res);
                gclass->type.type = res;
@@ -10682,17 +10728,20 @@ mono_reflection_create_unmanaged_type (MonoReflectionType *type)
        mono_error_set_pending_exception (&error);
 }
 
-void
-mono_reflection_register_with_runtime (MonoReflectionType *type)
+static gboolean
+reflection_register_with_runtime (MonoReflectionType *type, MonoError *error)
 {
-       MonoError error;
-       MonoType *res = mono_reflection_type_get_handle (type, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
        MonoDomain *domain = mono_object_domain ((MonoObject*)type);
        MonoClass *klass;
 
-       if (!res)
-               mono_raise_exception (mono_get_exception_argument (NULL, "Invalid generic instantiation, one or more arguments are not proper user types"));
+       mono_error_init (error);
+
+       MonoType *res = mono_reflection_type_get_handle (type, error);
+
+       if (!res && is_ok (error)) {
+               mono_error_set_argument (error, NULL, "Invalid generic instantiation, one or more arguments are not proper user types");
+       }
+       return_val_if_nok (error, FALSE);
 
        klass = mono_class_from_mono_type (res);
 
@@ -10709,25 +10758,39 @@ mono_reflection_register_with_runtime (MonoReflectionType *type)
        }
        mono_domain_unlock (domain);
        mono_loader_unlock ();
+
+       return TRUE;
+}
+
+void
+mono_reflection_register_with_runtime (MonoReflectionType *type)
+{
+       MonoError error;
+       (void) reflection_register_with_runtime (type, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 /**
  * LOCKING: Assumes the loader lock is held.
  */
 static MonoMethodSignature*
-parameters_to_signature (MonoImage *image, MonoArray *parameters) {
-       MonoError error;
+parameters_to_signature (MonoImage *image, MonoArray *parameters, MonoError *error) {
        MonoMethodSignature *sig;
        int count, i;
 
+       mono_error_init (error);
+
        count = parameters? mono_array_length (parameters): 0;
 
        sig = (MonoMethodSignature *)image_g_malloc0 (image, MONO_SIZEOF_METHOD_SIGNATURE + sizeof (MonoType*) * count);
        sig->param_count = count;
        sig->sentinelpos = -1; /* FIXME */
        for (i = 0; i < count; ++i) {
-               sig->params [i] = mono_type_array_get_and_resolve (parameters, i, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               sig->params [i] = mono_type_array_get_and_resolve (parameters, i, error);
+               if (!is_ok (error)) {
+                       image_g_free (image, sig);
+                       return NULL;
+               }
        }
        return sig;
 }
@@ -10736,10 +10799,13 @@ parameters_to_signature (MonoImage *image, MonoArray *parameters) {
  * LOCKING: Assumes the loader lock is held.
  */
 static MonoMethodSignature*
-ctor_builder_to_signature (MonoImage *image, MonoReflectionCtorBuilder *ctor) {
+ctor_builder_to_signature (MonoImage *image, MonoReflectionCtorBuilder *ctor, MonoError *error) {
        MonoMethodSignature *sig;
 
-       sig = parameters_to_signature (image, ctor->parameters);
+       mono_error_init (error);
+
+       sig = parameters_to_signature (image, ctor->parameters, error);
+       return_val_if_nok (error, NULL);
        sig->hasthis = ctor->attrs & METHOD_ATTRIBUTE_STATIC? 0: 1;
        sig->ret = &mono_defaults.void_class->byval_arg;
        return sig;
@@ -10749,15 +10815,20 @@ ctor_builder_to_signature (MonoImage *image, MonoReflectionCtorBuilder *ctor) {
  * LOCKING: Assumes the loader lock is held.
  */
 static MonoMethodSignature*
-method_builder_to_signature (MonoImage *image, MonoReflectionMethodBuilder *method) {
-       MonoError error;
+method_builder_to_signature (MonoImage *image, MonoReflectionMethodBuilder *method, MonoError *error) {
        MonoMethodSignature *sig;
 
-       sig = parameters_to_signature (image, method->parameters);
+       mono_error_init (error);
+
+       sig = parameters_to_signature (image, method->parameters, error);
+       return_val_if_nok (error, NULL);
        sig->hasthis = method->attrs & METHOD_ATTRIBUTE_STATIC? 0: 1;
        if (method->rtype) {
-               sig->ret = mono_reflection_type_get_handle ((MonoReflectionType*)method->rtype, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               sig->ret = mono_reflection_type_get_handle ((MonoReflectionType*)method->rtype, error);
+               if (!is_ok (error)) {
+                       image_g_free (image, sig);
+                       return NULL;
+               }
        } else {
                sig->ret = &mono_defaults.void_class->byval_arg;
        }
@@ -10766,15 +10837,20 @@ method_builder_to_signature (MonoImage *image, MonoReflectionMethodBuilder *meth
 }
 
 static MonoMethodSignature*
-dynamic_method_to_signature (MonoReflectionDynamicMethod *method) {
-       MonoError error;
+dynamic_method_to_signature (MonoReflectionDynamicMethod *method, MonoError *error) {
        MonoMethodSignature *sig;
 
-       sig = parameters_to_signature (NULL, method->parameters);
+       mono_error_init (error);
+
+       sig = parameters_to_signature (NULL, method->parameters, error);
+       return_val_if_nok (error, NULL);
        sig->hasthis = method->attrs & METHOD_ATTRIBUTE_STATIC? 0: 1;
        if (method->rtype) {
-               sig->ret = mono_reflection_type_get_handle (method->rtype, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               sig->ret = mono_reflection_type_get_handle (method->rtype, error);
+               if (!is_ok (error)) {
+                       g_free (sig);
+                       return NULL;
+               }
        } else {
                sig->ret = &mono_defaults.void_class->byval_arg;
        }
@@ -10783,15 +10859,14 @@ dynamic_method_to_signature (MonoReflectionDynamicMethod *method) {
 }
 
 static void
-get_prop_name_and_type (MonoObject *prop, char **name, MonoType **type)
+get_prop_name_and_type (MonoObject *prop, char **name, MonoType **type, MonoError *error)
 {
-       MonoError error;
+       mono_error_init (error);
        MonoClass *klass = mono_object_class (prop);
        if (strcmp (klass->name, "PropertyBuilder") == 0) {
                MonoReflectionPropertyBuilder *pb = (MonoReflectionPropertyBuilder *)prop;
                *name = mono_string_to_utf8 (pb->name);
-               *type = mono_reflection_type_get_handle ((MonoReflectionType*)pb->type, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               *type = mono_reflection_type_get_handle ((MonoReflectionType*)pb->type, error);
        } else {
                MonoReflectionProperty *p = (MonoReflectionProperty *)prop;
                *name = g_strdup (p->property->name);
@@ -10803,15 +10878,14 @@ get_prop_name_and_type (MonoObject *prop, char **name, MonoType **type)
 }
 
 static void
-get_field_name_and_type (MonoObject *field, char **name, MonoType **type)
+get_field_name_and_type (MonoObject *field, char **name, MonoType **type, MonoError *error)
 {
-       MonoError error;
+       mono_error_init (error);
        MonoClass *klass = mono_object_class (field);
        if (strcmp (klass->name, "FieldBuilder") == 0) {
                MonoReflectionFieldBuilder *fb = (MonoReflectionFieldBuilder *)field;
                *name = mono_string_to_utf8 (fb->name);
-               *type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               *type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
        } else {
                MonoReflectionField *f = (MonoReflectionField *)field;
                *name = g_strdup (mono_field_get_name (f->field));
@@ -10840,8 +10914,9 @@ is_sre_generic_instance (MonoClass *klass)
 }
 
 static void
-init_type_builder_generics (MonoObject *type)
+init_type_builder_generics (MonoObject *type, MonoError *error)
 {
+       mono_error_init (error);
 }
 
 #endif /* !DISABLE_REFLECTION_EMIT */
@@ -10907,14 +10982,15 @@ mono_reflection_type_resolve_user_types (MonoReflectionType *type, MonoError *er
                type = mono_reflection_type_get_underlying_system_type (type, error);
                return_val_if_nok (error, NULL);
                if (is_usertype (type)) {
-                       mono_error_set_generic_error (error, "System", "NotSupportedException", "User defined subclasses of System.Type are not yet supported22");
+                       mono_error_set_not_supported (error, "User defined subclasses of System.Type are not yet supported22");
                        return NULL;
                }
        }
 
        return type;
 }
-/*
+/**
+ * encode_cattr_value:
  * Encode a value in a custom attribute stream of bytes.
  * The value to encode is either supplied as an object in argument val
  * (valuetypes are boxed), or as a pointer to the data in the
@@ -10925,13 +11001,14 @@ mono_reflection_type_resolve_user_types (MonoReflectionType *type, MonoError *er
  * @buflen contains the size of the buffer and is used to return the new buffer size
  * if this needs to be realloced.
  * @retbuffer and @retp return the start and the position of the buffer
+ * @error set on error.
  */
 static void
-encode_cattr_value (MonoAssembly *assembly, char *buffer, char *p, char **retbuffer, char **retp, guint32 *buflen, MonoType *type, MonoObject *arg, char *argval)
+encode_cattr_value (MonoAssembly *assembly, char *buffer, char *p, char **retbuffer, char **retp, guint32 *buflen, MonoType *type, MonoObject *arg, char *argval, MonoError *error)
 {
-       MonoError error;
        MonoTypeEnum simple_type;
        
+       mono_error_init (error);
        if ((p-buffer) + 10 >= *buflen) {
                char *newbuf;
                *buflen *= 2;
@@ -11010,8 +11087,9 @@ handle_enum:
                        break;
                }
 handle_type:
-               arg_type = mono_reflection_type_get_handle ((MonoReflectionType*)arg, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               arg_type = mono_reflection_type_get_handle ((MonoReflectionType*)arg, error);
+               return_if_nok (error);
+
                str = type_get_qualified_name (arg_type, NULL);
                slen = strlen (str);
                if ((p-buffer) + 10 + slen >= *buflen) {
@@ -11054,19 +11132,22 @@ handle_type:
                        char *elptr = mono_array_addr ((MonoArray*)arg, char, 0);
                        int elsize = mono_class_array_element_size (arg_eclass);
                        for (i = 0; i < len; ++i) {
-                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &arg_eclass->byval_arg, NULL, elptr);
+                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &arg_eclass->byval_arg, NULL, elptr, error);
+                               return_if_nok (error);
                                elptr += elsize;
                        }
                } else if (eclass->valuetype && arg_eclass->valuetype) {
                        char *elptr = mono_array_addr ((MonoArray*)arg, char, 0);
                        int elsize = mono_class_array_element_size (eclass);
                        for (i = 0; i < len; ++i) {
-                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &eclass->byval_arg, NULL, elptr);
+                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &eclass->byval_arg, NULL, elptr, error);
+                               return_if_nok (error);
                                elptr += elsize;
                        }
                } else {
                        for (i = 0; i < len; ++i) {
-                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &eclass->byval_arg, mono_array_get ((MonoArray*)arg, MonoObject*, i), NULL);
+                               encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &eclass->byval_arg, mono_array_get ((MonoArray*)arg, MonoObject*, i), NULL, error);
+                               return_if_nok (error);
                        }
                }
                break;
@@ -11090,10 +11171,14 @@ handle_type:
                
                klass = mono_object_class (arg);
 
-               if (mono_object_isinst (arg, mono_defaults.systemtype_class)) {
+               if (mono_object_isinst_checked (arg, mono_defaults.systemtype_class, error)) {
                        *p++ = 0x50;
                        goto handle_type;
-               } else if (klass->enumtype) {
+               } else {
+                       return_if_nok (error);
+               }
+
+               if (klass->enumtype) {
                        *p++ = 0x55;
                } else if (klass == mono_defaults.string_class) {
                        simple_type = MONO_TYPE_STRING;
@@ -11106,7 +11191,8 @@ handle_type:
                                *p++ = 0x51;
                        else
                                *p++ = klass->element_class->byval_arg.type;
-                       encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &klass->byval_arg, arg, NULL);
+                       encode_cattr_value (assembly, buffer, p, &buffer, &p, buflen, &klass->byval_arg, arg, NULL, error);
+                       return_if_nok (error);
                        break;
                } else if (klass->byval_arg.type >= MONO_TYPE_BOOLEAN && klass->byval_arg.type <= MONO_TYPE_R8) {
                        *p++ = simple_type = klass->byval_arg.type;
@@ -11171,9 +11257,12 @@ encode_field_or_prop_type (MonoType *type, char *p, char **retp)
 
 #ifndef DISABLE_REFLECTION_EMIT
 static void
-encode_named_val (MonoReflectionAssembly *assembly, char *buffer, char *p, char **retbuffer, char **retp, guint32 *buflen, MonoType *type, char *name, MonoObject *value)
+encode_named_val (MonoReflectionAssembly *assembly, char *buffer, char *p, char **retbuffer, char **retp, guint32 *buflen, MonoType *type, char *name, MonoObject *value, MonoError *error)
 {
        int len;
+
+       mono_error_init (error);
+
        /* Preallocate a large enough buffer */
        if (type->type == MONO_TYPE_VALUETYPE && type->data.klass->enumtype) {
                char *str = type_get_qualified_name (type, NULL);
@@ -11203,12 +11292,13 @@ encode_named_val (MonoReflectionAssembly *assembly, char *buffer, char *p, char
        mono_metadata_encode_value (len, p, &p);
        memcpy (p, name, len);
        p += len;
-       encode_cattr_value (assembly->assembly, buffer, p, &buffer, &p, buflen, type, value, NULL);
+       encode_cattr_value (assembly->assembly, buffer, p, &buffer, &p, buflen, type, value, NULL, error);
+       return_if_nok (error);
        *retp = p;
        *retbuffer = buffer;
 }
 
-/*
+/**
  * mono_reflection_get_custom_attrs_blob:
  * @ctor: custom attribute constructor
  * @ctorArgs: arguments o the constructor
@@ -11224,15 +11314,44 @@ encode_named_val (MonoReflectionAssembly *assembly, char *buffer, char *p, char
 MonoArray*
 mono_reflection_get_custom_attrs_blob (MonoReflectionAssembly *assembly, MonoObject *ctor, MonoArray *ctorArgs, MonoArray *properties, MonoArray *propValues, MonoArray *fields, MonoArray* fieldValues) 
 {
-       MonoArray *result;
+       MonoError error;
+       MonoArray *result = mono_reflection_get_custom_attrs_blob_checked (assembly, ctor, ctorArgs, properties, propValues, fields, fieldValues, &error);
+       mono_error_cleanup (&error);
+       return result;
+}
+
+/**
+ * mono_reflection_get_custom_attrs_blob_checked:
+ * @ctor: custom attribute constructor
+ * @ctorArgs: arguments o the constructor
+ * @properties:
+ * @propValues:
+ * @fields:
+ * @fieldValues:
+ * @error: set on error
+ * 
+ * Creates the blob of data that needs to be saved in the metadata and that represents
+ * the custom attributed described by @ctor, @ctorArgs etc.
+ * Returns: a Byte array representing the blob of data.  On failure returns NULL and sets @error.
+ */
+MonoArray*
+mono_reflection_get_custom_attrs_blob_checked (MonoReflectionAssembly *assembly, MonoObject *ctor, MonoArray *ctorArgs, MonoArray *properties, MonoArray *propValues, MonoArray *fields, MonoArray* fieldValues, MonoError *error) 
+{
+       MonoArray *result = NULL;
        MonoMethodSignature *sig;
        MonoObject *arg;
        char *buffer, *p;
        guint32 buflen, i;
 
+       mono_error_init (error);
+
        if (strcmp (ctor->vtable->klass->name, "MonoCMethod")) {
                /* sig is freed later so allocate it in the heap */
-               sig = ctor_builder_to_signature (NULL, (MonoReflectionCtorBuilder*)ctor);
+               sig = ctor_builder_to_signature (NULL, (MonoReflectionCtorBuilder*)ctor, error);
+               if (!is_ok (error)) {
+                       g_free (sig);
+                       return NULL;
+               }
        } else {
                sig = mono_method_signature (((MonoReflectionMethod*)ctor)->method);
        }
@@ -11245,7 +11364,8 @@ mono_reflection_get_custom_attrs_blob (MonoReflectionAssembly *assembly, MonoObj
        *p++ = 0;
        for (i = 0; i < sig->param_count; ++i) {
                arg = mono_array_get (ctorArgs, MonoObject*, i);
-               encode_cattr_value (assembly->assembly, buffer, p, &buffer, &p, &buflen, sig->params [i], arg, NULL);
+               encode_cattr_value (assembly->assembly, buffer, p, &buffer, &p, &buflen, sig->params [i], arg, NULL, error);
+               if (!is_ok (error)) goto leave;
        }
        i = 0;
        if (properties)
@@ -11261,10 +11381,12 @@ mono_reflection_get_custom_attrs_blob (MonoReflectionAssembly *assembly, MonoObj
                        char *pname;
 
                        prop = (MonoObject *)mono_array_get (properties, gpointer, i);
-                       get_prop_name_and_type (prop, &pname, &ptype);
+                       get_prop_name_and_type (prop, &pname, &ptype, error);
+                       if (!is_ok (error)) goto leave;
                        *p++ = 0x54; /* PROPERTY signature */
-                       encode_named_val (assembly, buffer, p, &buffer, &p, &buflen, ptype, pname, (MonoObject*)mono_array_get (propValues, gpointer, i));
+                       encode_named_val (assembly, buffer, p, &buffer, &p, &buflen, ptype, pname, (MonoObject*)mono_array_get (propValues, gpointer, i), error);
                        g_free (pname);
+                       if (!is_ok (error)) goto leave;
                }
        }
 
@@ -11275,48 +11397,56 @@ mono_reflection_get_custom_attrs_blob (MonoReflectionAssembly *assembly, MonoObj
                        char *fname;
 
                        field = (MonoObject *)mono_array_get (fields, gpointer, i);
-                       get_field_name_and_type (field, &fname, &ftype);
+                       get_field_name_and_type (field, &fname, &ftype, error);
+                       if (!is_ok (error)) goto leave;
                        *p++ = 0x53; /* FIELD signature */
-                       encode_named_val (assembly, buffer, p, &buffer, &p, &buflen, ftype, fname, (MonoObject*)mono_array_get (fieldValues, gpointer, i));
+                       encode_named_val (assembly, buffer, p, &buffer, &p, &buflen, ftype, fname, (MonoObject*)mono_array_get (fieldValues, gpointer, i), error);
                        g_free (fname);
+                       if (!is_ok (error)) goto leave;
                }
        }
 
        g_assert (p - buffer <= buflen);
        buflen = p - buffer;
-       result = mono_array_new (mono_domain_get (), mono_defaults.byte_class, buflen);
+       result = mono_array_new_checked (mono_domain_get (), mono_defaults.byte_class, buflen, error);
+       if (!is_ok (error))
+               goto leave;
        p = mono_array_addr (result, char, 0);
        memcpy (p, buffer, buflen);
+leave:
        g_free (buffer);
        if (strcmp (ctor->vtable->klass->name, "MonoCMethod"))
                g_free (sig);
        return result;
 }
 
-/*
- * mono_reflection_setup_internal_class:
+/**
+ * reflection_setup_internal_class:
  * @tb: a TypeBuilder object
+ * @error: set on error
  *
  * Creates a MonoClass that represents the TypeBuilder.
  * This is a trick that lets us simplify a lot of reflection code
  * (and will allow us to support Build and Run assemblies easier).
+ *
+ * Returns TRUE on success. On failure, returns FALSE and sets @error.
  */
-void
-mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
+static gboolean
+reflection_setup_internal_class (MonoReflectionTypeBuilder *tb, MonoError *error)
 {
-       MonoError error;
        MonoClass *klass, *parent;
 
-       RESOLVE_TYPE (tb->parent, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_init (error);
+       RESOLVE_TYPE (tb->parent, error);
+       return_val_if_nok (error, FALSE);
 
        mono_loader_lock ();
 
        if (tb->parent) {
-               MonoType *parent_type = mono_reflection_type_get_handle ((MonoReflectionType*)tb->parent, &error);
-               if (!is_ok (&error)) {
+               MonoType *parent_type = mono_reflection_type_get_handle ((MonoReflectionType*)tb->parent, error);
+               if (!is_ok (error)) {
                        mono_loader_unlock ();
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return FALSE;
                }
                /* check so we can compile corlib correctly */
                if (strcmp (mono_object_class (tb->parent)->name, "TypeBuilder") == 0) {
@@ -11338,7 +11468,7 @@ mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
                mono_class_setup_parent (klass, parent);
                mono_class_setup_mono_type (klass);
                mono_loader_unlock ();
-               return;
+               return TRUE;
        }
 
        klass = (MonoClass *)mono_image_alloc0 (&tb->module->dynamic_image->image, sizeof (MonoClass));
@@ -11346,11 +11476,11 @@ mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
        klass->image = &tb->module->dynamic_image->image;
 
        klass->inited = 1; /* we lie to the runtime */
-       klass->name = mono_string_to_utf8_image (klass->image, tb->name, &error);
-       if (!mono_error_ok (&error))
+       klass->name = mono_string_to_utf8_image (klass->image, tb->name, error);
+       if (!is_ok (error))
                goto failure;
-       klass->name_space = mono_string_to_utf8_image (klass->image, tb->nspace, &error);
-       if (!mono_error_ok (&error))
+       klass->name_space = mono_string_to_utf8_image (klass->image, tb->nspace, error);
+       if (!is_ok (error))
                goto failure;
        klass->type_token = MONO_TOKEN_TYPE_DEF | tb->table_idx;
        klass->flags = tb->attrs;
@@ -11411,8 +11541,8 @@ mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
 
        if (tb->nesting_type) {
                g_assert (tb->nesting_type->type);
-               MonoType *nesting_type = mono_reflection_type_get_handle (tb->nesting_type, &error);
-               if (!is_ok (&error)) goto failure;
+               MonoType *nesting_type = mono_reflection_type_get_handle (tb->nesting_type, error);
+               if (!is_ok (error)) goto failure;
                klass->nested_in = mono_class_from_mono_type (nesting_type);
        }
 
@@ -11421,11 +11551,29 @@ mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
        mono_profiler_class_loaded (klass, MONO_PROFILE_OK);
        
        mono_loader_unlock ();
-       return;
+       return TRUE;
 
 failure:
        mono_loader_unlock ();
-       mono_error_raise_exception (&error);
+       return FALSE;
+}
+
+/**
+ * mono_reflection_setup_internal_class:
+ * @tb: a TypeBuilder object
+ *
+ * (icall)
+ * Creates a MonoClass that represents the TypeBuilder.
+ * This is a trick that lets us simplify a lot of reflection code
+ * (and will allow us to support Build and Run assemblies easier).
+ *
+ */
+void
+mono_reflection_setup_internal_class (MonoReflectionTypeBuilder *tb)
+{
+       MonoError error;
+       (void) reflection_setup_internal_class (tb, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 /*
@@ -11439,25 +11587,30 @@ mono_reflection_setup_generic_class (MonoReflectionTypeBuilder *tb)
 {
 }
 
-/*
+/**
  * mono_reflection_create_generic_class:
  * @tb: a TypeBuilder object
+ * @error: set on error
  *
  * Creates the generic class after all generic parameters have been added.
+ * On success returns TRUE, on failure returns FALSE and sets @error.
+ * 
  */
-void
-mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb)
+gboolean
+mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb, MonoError *error)
 {
-       MonoError error;
+
        MonoClass *klass;
        int count, i;
 
+       mono_error_init (error);
+
        klass = mono_class_from_mono_type (tb->type.type);
 
        count = tb->generic_params ? mono_array_length (tb->generic_params) : 0;
 
        if (klass->generic_container || (count == 0))
-               return;
+               return TRUE;
 
        g_assert (tb->generic_container && (tb->generic_container->owner.klass == klass));
 
@@ -11471,8 +11624,8 @@ mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb)
 
        for (i = 0; i < count; i++) {
                MonoReflectionGenericParam *gparam = (MonoReflectionGenericParam *)mono_array_get (tb->generic_params, gpointer, i);
-               MonoType *param_type = mono_reflection_type_get_handle ((MonoReflectionType*)gparam, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *param_type = mono_reflection_type_get_handle ((MonoReflectionType*)gparam, error);
+               return_val_if_nok (error, FALSE);
                MonoGenericParamFull *param = (MonoGenericParamFull *) param_type->data.generic_param;
                klass->generic_container->type_params [i] = *param;
                /*Make sure we are a diferent type instance */
@@ -11484,20 +11637,25 @@ mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb)
        }
 
        klass->generic_container->context.class_inst = mono_get_shared_generic_inst (klass->generic_container);
+       return TRUE;
 }
 
-/*
- * mono_reflection_create_internal_class:
+/**
+ * reflection_create_internal_class:
  * @tb: a TypeBuilder object
+ * @error: set on error
  *
  * Actually create the MonoClass that is associated with the TypeBuilder.
+ * On success returns TRUE, on failure returns FALSE and sets @error.
+ *
  */
-void
-mono_reflection_create_internal_class (MonoReflectionTypeBuilder *tb)
+static gboolean
+reflection_create_internal_class (MonoReflectionTypeBuilder *tb, MonoError *error)
 {
-       MonoError error;
+
        MonoClass *klass;
 
+       mono_error_init (error);
        klass = mono_class_from_mono_type (tb->type.type);
 
        mono_loader_lock ();
@@ -11511,20 +11669,20 @@ mono_reflection_create_internal_class (MonoReflectionTypeBuilder *tb)
 
                fb = mono_array_get (tb->fields, MonoReflectionFieldBuilder*, 0);
 
-               MonoType *field_type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, &error);
-               if (!is_ok (&error)) {
+               MonoType *field_type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
+               if (!is_ok (error)) {
                        mono_loader_unlock ();
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return FALSE;
                }
                if (!mono_type_is_valid_enum_basetype (field_type)) {
                        mono_loader_unlock ();
-                       return;
+                       return TRUE;
                }
 
-               enum_basetype = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, &error);
-               if (!is_ok (&error)) {
+               enum_basetype = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
+               if (!is_ok (error)) {
                        mono_loader_unlock ();
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return FALSE;
                }
                klass->element_class = mono_class_from_mono_type (enum_basetype);
                if (!klass->element_class)
@@ -11544,15 +11702,32 @@ mono_reflection_create_internal_class (MonoReflectionTypeBuilder *tb)
                mono_class_setup_vtable_general (klass, NULL, 0, NULL);
        }
        mono_loader_unlock ();
+       return TRUE;
+}
+
+/**
+ * mono_reflection_create_internal_class:
+ * @tb: a TypeBuilder object
+ *
+ * (icall)
+ * Actually create the MonoClass that is associated with the TypeBuilder.
+ */
+void
+mono_reflection_create_internal_class (MonoReflectionTypeBuilder *tb)
+{
+       MonoError error;
+       (void) reflection_create_internal_class (tb, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 static MonoMarshalSpec*
 mono_marshal_spec_from_builder (MonoImage *image, MonoAssembly *assembly,
-                                                               MonoReflectionMarshal *minfo)
+                               MonoReflectionMarshal *minfo, MonoError *error)
 {
-       MonoError error;
        MonoMarshalSpec *res;
 
+       mono_error_init (error);
+
        res = image_g_new0 (image, MonoMarshalSpec, 1);
        res->native = (MonoMarshalNative)minfo->type;
 
@@ -11578,8 +11753,11 @@ mono_marshal_spec_from_builder (MonoImage *image, MonoAssembly *assembly,
 
        case MONO_NATIVE_CUSTOM:
                if (minfo->marshaltyperef) {
-                       MonoType *marshaltyperef = mono_reflection_type_get_handle ((MonoReflectionType*)minfo->marshaltyperef, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *marshaltyperef = mono_reflection_type_get_handle ((MonoReflectionType*)minfo->marshaltyperef, error);
+                       if (!is_ok (error)) {
+                               image_g_free (image, res);
+                               return NULL;
+                       }
                        res->data.custom_data.custom_name =
                                type_get_fully_qualified_name (marshaltyperef);
                }
@@ -11653,9 +11831,9 @@ mono_reflection_marshal_as_attribute_from_marshal_spec (MonoDomain *domain, Mono
 static MonoMethod*
 reflection_methodbuilder_to_mono_method (MonoClass *klass,
                                         ReflectionMethodBuilder *rmb,
-                                        MonoMethodSignature *sig)
+                                        MonoMethodSignature *sig,
+                                        MonoError *error)
 {
-       MonoError error;
        MonoMethod *m;
        MonoMethodWrapper *wrapperm;
        MonoMarshalSpec **specs;
@@ -11664,7 +11842,7 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
        gboolean dynamic;
        int i;
 
-       mono_error_init (&error);
+       mono_error_init (error);
        /*
         * Methods created using a MethodBuilder should have their memory allocated
         * inside the image mempool, while dynamic methods should have their memory
@@ -11708,10 +11886,10 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
 
                method_aux = image_g_new0 (image, MonoReflectionMethodAux, 1);
 
-               method_aux->dllentry = rmb->dllentry ? mono_string_to_utf8_image (image, rmb->dllentry, &error) : image_strdup (image, m->name);
-               g_assert (mono_error_ok (&error));
-               method_aux->dll = mono_string_to_utf8_image (image, rmb->dll, &error);
-               g_assert (mono_error_ok (&error));
+               method_aux->dllentry = rmb->dllentry ? mono_string_to_utf8_image (image, rmb->dllentry, error) : image_strdup (image, m->name);
+               mono_error_assert_ok (error);
+               method_aux->dll = mono_string_to_utf8_image (image, rmb->dll, error);
+               mono_error_assert_ok (error);
                
                ((MonoMethodPInvoke*)m)->piflags = (rmb->native_cc << 8) | (rmb->charset ? (rmb->charset - 1) * 2 : 0) | rmb->extra_flags;
 
@@ -11764,16 +11942,16 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
                                mono_array_get (rmb->ilgen->locals, MonoReflectionLocalBuilder*, i);
 
                        header->locals [i] = image_g_new0 (image, MonoType, 1);
-                       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)lb->type, &error);
-                       mono_error_assert_ok (&error);
+                       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)lb->type, error);
+                       mono_error_assert_ok (error);
                        memcpy (header->locals [i], type, MONO_SIZEOF_TYPE);
                }
 
                header->num_clauses = num_clauses;
                if (num_clauses) {
                        header->clauses = method_encode_clauses (image, (MonoDynamicImage*)klass->image,
-                                                                rmb->ilgen, num_clauses, &error);
-                       mono_error_assert_ok (&error);
+                                                                rmb->ilgen, num_clauses, error);
+                       mono_error_assert_ok (error);
                }
 
                wrapperm->header = header;
@@ -11796,8 +11974,8 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
                for (i = 0; i < count; i++) {
                        MonoReflectionGenericParam *gp =
                                mono_array_get (rmb->generic_params, MonoReflectionGenericParam*, i);
-                       MonoType *gp_type = mono_reflection_type_get_handle ((MonoReflectionType*)gp, &error);
-                       mono_error_assert_ok (&error);
+                       MonoType *gp_type = mono_reflection_type_get_handle ((MonoReflectionType*)gp, error);
+                       mono_error_assert_ok (error);
                        MonoGenericParamFull *param = (MonoGenericParamFull *) gp_type->data.generic_param;
                        container->type_params [i] = *param;
                }
@@ -11878,8 +12056,8 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
                                }
 
                                if (pb->name) {
-                                       method_aux->param_names [i] = mono_string_to_utf8_image (image, pb->name, &error);
-                                       g_assert (mono_error_ok (&error));
+                                       method_aux->param_names [i] = mono_string_to_utf8_image (image, pb->name, error);
+                                       mono_error_assert_ok (error);
                                }
                                if (pb->cattrs) {
                                        if (!method_aux->param_cattr)
@@ -11900,7 +12078,13 @@ reflection_methodbuilder_to_mono_method (MonoClass *klass,
                                        if (specs == NULL)
                                                specs = image_g_new0 (image, MonoMarshalSpec*, sig->param_count + 1);
                                        specs [pb->position] = 
-                                               mono_marshal_spec_from_builder (image, klass->image->assembly, pb->marshal_info);
+                                               mono_marshal_spec_from_builder (image, klass->image->assembly, pb->marshal_info, error);
+                                       if (!is_ok (error)) {
+                                               mono_loader_unlock ();
+                                               image_g_free (image, specs);
+                                               /* FIXME: if image is NULL, this leaks all the other stuff we alloc'd in this function */
+                                               return NULL;
+                                       }
                                }
                        }
                }
@@ -11925,13 +12109,16 @@ ctorbuilder_to_mono_method (MonoClass *klass, MonoReflectionCtorBuilder* mb, Mon
        MonoMethodSignature *sig;
 
        mono_loader_lock ();
-       sig = ctor_builder_to_signature (klass->image, mb);
+       g_assert (klass->image != NULL);
+       sig = ctor_builder_to_signature (klass->image, mb, error);
        mono_loader_unlock ();
+       return_val_if_nok (error, NULL);
 
        if (!reflection_methodbuilder_from_ctor_builder (&rmb, mb, error))
                return NULL;
 
-       mb->mhandle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig);
+       mb->mhandle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig, error);
+       return_val_if_nok (error, NULL);
        mono_save_custom_attrs (klass->image, mb->mhandle, mb->cattrs);
 
        /* If we are in a generic class, we might be called multiple times from inflate_method */
@@ -11952,13 +12139,16 @@ methodbuilder_to_mono_method (MonoClass *klass, MonoReflectionMethodBuilder* mb,
        mono_error_init (error);
 
        mono_loader_lock ();
-       sig = method_builder_to_signature (klass->image, mb);
+       g_assert (klass->image != NULL);
+       sig = method_builder_to_signature (klass->image, mb, error);
        mono_loader_unlock ();
+       return_val_if_nok (error, NULL);
 
        if (!reflection_methodbuilder_from_method_builder (&rmb, mb, error))
                return NULL;
 
-       mb->mhandle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig);
+       mb->mhandle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig, error);
+       return_val_if_nok (error, NULL);
        mono_save_custom_attrs (klass->image, mb->mhandle, mb->cattrs);
 
        /* If we are in a generic class, we might be called multiple times from inflate_method */
@@ -11970,39 +12160,40 @@ methodbuilder_to_mono_method (MonoClass *klass, MonoReflectionMethodBuilder* mb,
 }
 
 static MonoClassField*
-fieldbuilder_to_mono_class_field (MonoClass *klass, MonoReflectionFieldBuilder* fb)
+fieldbuilder_to_mono_class_field (MonoClass *klass, MonoReflectionFieldBuilder* fb, MonoError *error)
 {
        MonoClassField *field;
        MonoType *custom;
-       MonoError error;
+
+       mono_error_init (error);
 
        field = g_new0 (MonoClassField, 1);
 
-       field->name = mono_string_to_utf8_image (klass->image, fb->name, &error);
-       g_assert (mono_error_ok (&error));
+       field->name = mono_string_to_utf8_image (klass->image, fb->name, error);
+       mono_error_assert_ok (error);
        if (fb->attrs || fb->modreq || fb->modopt) {
-               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, &error);
-               if (!is_ok (&error)) {
+               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
+               if (!is_ok (error)) {
                        g_free (field);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return NULL;
                }
                field->type = mono_metadata_type_dup (NULL, type);
                field->type->attrs = fb->attrs;
 
                g_assert (image_is_dynamic (klass->image));
-               custom = add_custom_modifiers ((MonoDynamicImage*)klass->image, field->type, fb->modreq, fb->modopt, &error);
+               custom = add_custom_modifiers ((MonoDynamicImage*)klass->image, field->type, fb->modreq, fb->modopt, error);
                g_free (field->type);
-               if (!is_ok (&error)) {
+               if (!is_ok (error)) {
                        g_free (field);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return NULL;
                }
                field->type = mono_metadata_type_dup (klass->image, custom);
                g_free (custom);
        } else {
-               field->type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, &error);
-               if (!is_ok (&error)) {
+               field->type = mono_reflection_type_get_handle ((MonoReflectionType*)fb->type, error);
+               if (!is_ok (error)) {
                        g_free (field);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return NULL;
                }
        }
        if (fb->offset != -1)
@@ -12016,15 +12207,26 @@ fieldbuilder_to_mono_class_field (MonoClass *klass, MonoReflectionFieldBuilder*
 }
 #endif
 
+/**
+ * mono_reflection_bind_generic_parameters:
+ * @type: a managed type object (which should be some kind of generic (instance? definition?))
+ * @type_args: the number of type arguments to bind
+ * @types: array of type arguments
+ * @error: set on error
+ *
+ * Given a managed type object for a generic type instance, binds each of its arguments to the specified types.
+ * Returns the MonoType* for the resulting type instantiation.  On failure returns NULL and sets @error.
+ */
 MonoType*
-mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc, MonoType **types)
+mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc, MonoType **types, MonoError *error)
 {
-       MonoError error;
        MonoClass *klass;
        MonoReflectionTypeBuilder *tb = NULL;
        gboolean is_dynamic = FALSE;
        MonoClass *geninst;
 
+       mono_error_init (error);
+       
        mono_loader_lock ();
 
        if (is_sre_type_builder (mono_object_class (type))) {
@@ -12042,15 +12244,23 @@ mono_reflection_bind_generic_parameters (MonoReflectionType *type, int type_argc
        }
 
        /* FIXME: fix the CreateGenericParameters protocol to avoid the two stage setup of TypeBuilders */
-       if (tb && tb->generic_container)
-               mono_reflection_create_generic_class (tb);
+       if (tb && tb->generic_container) {
+               if (!mono_reflection_create_generic_class (tb, error)) {
+                       mono_loader_unlock ();
+                       return NULL;
+               }
+       }
 
-       MonoType *t = mono_reflection_type_get_handle (type, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoType *t = mono_reflection_type_get_handle (type, error);
+       if (!is_ok (error)) {
+               mono_loader_unlock ();
+               return NULL;
+       }
 
        klass = mono_class_from_mono_type (t);
        if (!klass->generic_container) {
                mono_loader_unlock ();
+               mono_error_set_type_load_class (error, klass, "Cannot bind generic parameters of a non-generic type");
                return NULL;
        }
 
@@ -12081,10 +12291,9 @@ mono_class_bind_generic_parameters (MonoClass *klass, int type_argc, MonoType **
        return mono_generic_class_get_class (gclass);
 }
 
-MonoReflectionMethod*
-mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, MonoArray *types)
+static MonoReflectionMethod*
+reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, MonoArray *types, MonoError *error)
 {
-       MonoError error;
        MonoClass *klass;
        MonoMethod *method, *inflated;
        MonoMethodInflated *imethod;
@@ -12093,6 +12302,8 @@ mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, M
        MonoType **type_argv;
        int count, i;
 
+       mono_error_init (error);
+
        /*FIXME but this no longer should happen*/
        if (!strcmp (rmethod->object.vtable->klass->name, "MethodBuilder")) {
 #ifndef DISABLE_REFLECTION_EMIT
@@ -12101,13 +12312,12 @@ mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, M
                MonoClass *klass;
 
                mb = (MonoReflectionMethodBuilder *) rmethod;
-               tb = mono_reflection_type_get_handle ((MonoReflectionType*)mb->type, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               tb = mono_reflection_type_get_handle ((MonoReflectionType*)mb->type, error);
+               return_val_if_nok (error, NULL);
                klass = mono_class_from_mono_type (tb);
 
-               method = methodbuilder_to_mono_method (klass, mb, &error);
-               if (!method)
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+               method = methodbuilder_to_mono_method (klass, mb, error);
+               return_val_if_nok (error, NULL);
 #else
                g_assert_not_reached ();
                method = NULL;
@@ -12128,10 +12338,10 @@ mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, M
        type_argv = g_new0 (MonoType *, count);
        for (i = 0; i < count; i++) {
                MonoReflectionType *garg = (MonoReflectionType *)mono_array_get (types, gpointer, i);
-               type_argv [i] = mono_reflection_type_get_handle (garg, &error);
-               if (!is_ok (&error)) {
+               type_argv [i] = mono_reflection_type_get_handle (garg, error);
+               if (!is_ok (error)) {
                        g_free (type_argv);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return NULL;
                }
        }
        ginst = mono_metadata_get_generic_inst (count, type_argv);
@@ -12140,8 +12350,8 @@ mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, M
        tmp_context.class_inst = klass->generic_class ? klass->generic_class->context.class_inst : NULL;
        tmp_context.method_inst = ginst;
 
-       inflated = mono_class_inflate_generic_method_checked (method, &tmp_context, &error);
-       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+       inflated = mono_class_inflate_generic_method_checked (method, &tmp_context, error);
+       mono_error_assert_ok (error);
        imethod = (MonoMethodInflated *) inflated;
 
        /*FIXME but I think this is no longer necessary*/
@@ -12156,14 +12366,25 @@ mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, M
                mono_image_unlock ((MonoImage*)image);
        }
 
-       if (!mono_verifier_is_method_valid_generic_instantiation (inflated))
-               mono_raise_exception (mono_get_exception_argument ("typeArguments", "Invalid generic arguments"));
+       if (!mono_verifier_is_method_valid_generic_instantiation (inflated)) {
+               mono_error_set_argument (error, "typeArguments", "Invalid generic arguments");
+               return NULL;
+       }
        
-       MonoReflectionMethod *ret = mono_method_get_object_checked (mono_object_domain (rmethod), inflated, NULL, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoReflectionMethod *ret = mono_method_get_object_checked (mono_object_domain (rmethod), inflated, NULL, error);
        return ret;
 }
 
+MonoReflectionMethod*
+mono_reflection_bind_generic_method_parameters (MonoReflectionMethod *rmethod, MonoArray *types)
+{
+       MonoError error;
+       MonoReflectionMethod *result = reflection_bind_generic_method_parameters (rmethod, types, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
+
 #ifndef DISABLE_REFLECTION_EMIT
 
 static MonoMethod *
@@ -12259,29 +12480,30 @@ inflate_method (MonoReflectionType *type, MonoObject *obj, MonoError *error)
 }
 
 /*TODO avoid saving custom attrs for generic classes as it's enough to have them on the generic type definition.*/
-void
-mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, MonoArray *fields)
+static gboolean
+reflection_generic_class_initialize (MonoReflectionGenericClass *type, MonoArray *fields, MonoError *error)
 {
-       MonoError error;
        MonoGenericClass *gclass;
        MonoDynamicGenericClass *dgclass;
        MonoClass *klass, *gklass;
        MonoType *gtype;
        int i;
 
-       gtype = mono_reflection_type_get_handle ((MonoReflectionType*)type, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_init (error);
+
+       gtype = mono_reflection_type_get_handle ((MonoReflectionType*)type, error);
+       return_val_if_nok (error, FALSE);
        klass = mono_class_from_mono_type (gtype);
        g_assert (gtype->type == MONO_TYPE_GENERICINST);
        gclass = gtype->data.generic_class;
 
        if (!gclass->is_dynamic)
-               return;
+               return TRUE;
 
        dgclass = (MonoDynamicGenericClass *) gclass;
 
        if (dgclass->initialized)
-               return;
+               return TRUE;
 
        gklass = gclass->container_class;
        mono_class_init (gklass);
@@ -12293,13 +12515,13 @@ mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, Mono
        dgclass->field_generic_types = mono_image_set_new0 (gclass->owner, MonoType*, dgclass->count_fields);
 
        for (i = 0; i < dgclass->count_fields; i++) {
-               MonoError error;
                MonoObject *obj = (MonoObject *)mono_array_get (fields, gpointer, i);
                MonoClassField *field, *inflated_field = NULL;
 
-               if (!strcmp (obj->vtable->klass->name, "FieldBuilder"))
-                       inflated_field = field = fieldbuilder_to_mono_class_field (klass, (MonoReflectionFieldBuilder *) obj);
-               else if (!strcmp (obj->vtable->klass->name, "MonoField"))
+               if (!strcmp (obj->vtable->klass->name, "FieldBuilder")) {
+                       inflated_field = field = fieldbuilder_to_mono_class_field (klass, (MonoReflectionFieldBuilder *) obj, error);
+                       return_val_if_nok (error, FALSE);
+               } else if (!strcmp (obj->vtable->klass->name, "MonoField"))
                        field = ((MonoReflectionField *) obj)->field;
                else {
                        field = NULL; /* prevent compiler warning */
@@ -12309,8 +12531,8 @@ mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, Mono
                dgclass->fields [i] = *field;
                dgclass->fields [i].parent = klass;
                dgclass->fields [i].type = mono_class_inflate_generic_type_checked (
-                       field->type, mono_generic_class_get_context ((MonoGenericClass *) dgclass), &error);
-               mono_error_assert_ok (&error); /* FIXME don't swallow the error */
+                       field->type, mono_generic_class_get_context ((MonoGenericClass *) dgclass), error);
+               mono_error_assert_ok (error); /* FIXME don't swallow the error */
                dgclass->field_generic_types [i] = field->type;
                MONO_GC_REGISTER_ROOT_IF_MOVING (dgclass->field_objects [i], MONO_ROOT_SOURCE_REFLECTION, "dynamic generic class field object");
                dgclass->field_objects [i] = obj;
@@ -12323,6 +12545,15 @@ mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, Mono
        }
 
        dgclass->initialized = TRUE;
+       return TRUE;
+}
+
+void
+mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, MonoArray *fields)
+{
+       MonoError error;
+       (void) reflection_generic_class_initialize (type, fields, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 void
@@ -12342,21 +12573,34 @@ mono_reflection_free_dynamic_generic_class (MonoGenericClass *gclass)
        }
 }
 
-static void
-fix_partial_generic_class (MonoClass *klass)
+/**
+ * fix_partial_generic_class:
+ * @klass: a generic instantiation MonoClass
+ * @error: set on error
+ *
+ * Assumes that the generic container of @klass has its vtable
+ * initialized, and updates the parent class, insterfaces, methods and
+ * fields of @klass by inflating the types using the generic context.
+ *
+ * On success returns TRUE, on failure returns FALSE and sets @error.
+ *
+ */
+static gboolean
+fix_partial_generic_class (MonoClass *klass, MonoError *error)
 {
        MonoClass *gklass = klass->generic_class->container_class;
        MonoDynamicGenericClass *dgclass;
        int i;
 
+       mono_error_init (error);
+
        if (klass->wastypebuilder)
-               return;
+               return TRUE;
 
        dgclass = (MonoDynamicGenericClass *)  klass->generic_class;
        if (klass->parent != gklass->parent) {
-               MonoError error;
-               MonoType *parent_type = mono_class_inflate_generic_type_checked (&gklass->parent->byval_arg, &klass->generic_class->context, &error);
-               if (mono_error_ok (&error)) {
+               MonoType *parent_type = mono_class_inflate_generic_type_checked (&gklass->parent->byval_arg, &klass->generic_class->context, error);
+               if (mono_error_ok (error)) {
                        MonoClass *parent = mono_class_from_mono_type (parent_type);
                        mono_metadata_free_type (parent_type);
                        if (parent != klass->parent) {
@@ -12365,26 +12609,23 @@ fix_partial_generic_class (MonoClass *klass)
                                mono_class_setup_parent (klass, parent);
                        }
                } else {
-                       mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
-                       mono_error_cleanup (&error);
                        if (gklass->wastypebuilder)
                                klass->wastypebuilder = TRUE;
-                       return;
+                       return FALSE;
                }
        }
 
        if (!dgclass->initialized)
-               return;
+               return TRUE;
 
        if (klass->method.count != gklass->method.count) {
                klass->method.count = gklass->method.count;
                klass->methods = (MonoMethod **)mono_image_alloc (klass->image, sizeof (MonoMethod*) * (klass->method.count + 1));
 
                for (i = 0; i < klass->method.count; i++) {
-                       MonoError error;
                        klass->methods [i] = mono_class_inflate_generic_method_full_checked (
-                               gklass->methods [i], klass, mono_class_get_context (klass), &error);
-                       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+                               gklass->methods [i], klass, mono_class_get_context (klass), error);
+                       mono_error_assert_ok (error);
                }
        }
 
@@ -12394,15 +12635,14 @@ fix_partial_generic_class (MonoClass *klass)
                klass->interfaces_packed = NULL; /*make setup_interface_offsets happy*/
 
                for (i = 0; i < gklass->interface_count; ++i) {
-                       MonoError error;
-                       MonoType *iface_type = mono_class_inflate_generic_type_checked (&gklass->interfaces [i]->byval_arg, mono_class_get_context (klass), &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *iface_type = mono_class_inflate_generic_type_checked (&gklass->interfaces [i]->byval_arg, mono_class_get_context (klass), error);
+                       return_val_if_nok (error, FALSE);
 
                        klass->interfaces [i] = mono_class_from_mono_type (iface_type);
                        mono_metadata_free_type (iface_type);
 
-                       ensure_runtime_vtable (klass->interfaces [i], &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       if (!ensure_runtime_vtable (klass->interfaces [i], error))
+                               return FALSE;
                }
                klass->interfaces_inited = 1;
        }
@@ -12412,18 +12652,17 @@ fix_partial_generic_class (MonoClass *klass)
                klass->fields = image_g_new0 (klass->image, MonoClassField, klass->field.count);
 
                for (i = 0; i < klass->field.count; i++) {
-                       MonoError error;
                        klass->fields [i] = gklass->fields [i];
                        klass->fields [i].parent = klass;
-                       klass->fields [i].type = mono_class_inflate_generic_type_checked (gklass->fields [i].type, mono_class_get_context (klass), &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       klass->fields [i].type = mono_class_inflate_generic_type_checked (gklass->fields [i].type, mono_class_get_context (klass), error);
+                       return_val_if_nok (error, FALSE);
                }
        }
 
        /*We can only finish with this klass once it's parent has as well*/
        if (gklass->wastypebuilder)
                klass->wastypebuilder = TRUE;
-       return;
+       return TRUE;
 }
 
 /**
@@ -12444,9 +12683,7 @@ ensure_generic_class_runtime_vtable (MonoClass *klass, MonoError *error)
        if (!ensure_runtime_vtable (gklass, error))
                return FALSE;
 
-       fix_partial_generic_class (klass);
-
-       return TRUE;
+       return fix_partial_generic_class (klass, error);
 }
 
 /**
@@ -12505,8 +12742,10 @@ ensure_runtime_vtable (MonoClass *klass, MonoError *error)
                        klass->interfaces_inited = 1;
                }
        } else if (klass->generic_class){
-               if (!ensure_generic_class_runtime_vtable (klass, error))
+               if (!ensure_generic_class_runtime_vtable (klass, error)) {
+                       mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
                        return FALSE;
+               }
        }
 
        if (klass->flags & TYPE_ATTRIBUTE_INTERFACE) {
@@ -12537,9 +12776,9 @@ ensure_runtime_vtable (MonoClass *klass, MonoError *error)
 }
 
 static MonoMethod*
-mono_reflection_method_get_handle (MonoObject *method)
+mono_reflection_method_get_handle (MonoObject *method, MonoError *error)
 {
-       MonoError error;
+       mono_error_init (error);
        MonoClass *klass = mono_object_class (method);
        if (is_sr_mono_method (klass) || is_sr_mono_generic_method (klass)) {
                MonoReflectionMethod *sr_method = (MonoReflectionMethod*)method;
@@ -12554,11 +12793,10 @@ mono_reflection_method_get_handle (MonoObject *method)
                MonoMethod *result;
                /*FIXME move this to a proper method and unify with resolve_object*/
                if (m->method_args) {
-                       result = mono_reflection_method_on_tb_inst_get_handle (m, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       result = mono_reflection_method_on_tb_inst_get_handle (m, error);
                } else {
-                       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)m->inst, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)m->inst, error);
+                       return_val_if_nok (error, NULL);
                        MonoClass *inflated_klass = mono_class_from_mono_type (type);
                        MonoMethod *mono_method;
 
@@ -12579,12 +12817,13 @@ mono_reflection_method_get_handle (MonoObject *method)
 }
 
 void
-mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides)
+mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides, MonoError *error)
 {
        MonoReflectionTypeBuilder *tb;
        int i, j, onum;
        MonoReflectionMethod *m;
 
+       mono_error_init (error);
        *overrides = NULL;
        *num_overrides = 0;
 
@@ -12618,7 +12857,8 @@ mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides
                                for (j = 0; j < mono_array_length (mb->override_methods); ++j) {
                                        m = mono_array_get (mb->override_methods, MonoReflectionMethod*, j);
 
-                                       (*overrides) [onum * 2] = mono_reflection_method_get_handle ((MonoObject*)m);
+                                       (*overrides) [onum * 2] = mono_reflection_method_get_handle ((MonoObject*)m, error);
+                                       return_if_nok (error);
                                        (*overrides) [onum * 2 + 1] = mb->mhandle;
 
                                        g_assert (mb->mhandle);
@@ -12722,7 +12962,7 @@ typebuilder_setup_fields (MonoClass *klass, MonoError *error)
        }
 
        klass->instance_size = MAX (klass->instance_size, real_size);
-       mono_class_layout_fields (klass);
+       mono_class_layout_fields (klass, klass->instance_size);
 }
 
 static void
@@ -12775,15 +13015,19 @@ typebuilder_setup_properties (MonoClass *klass, MonoError *error)
        }
 }
 
-MonoReflectionEvent *
-mono_reflection_event_builder_get_event_info (MonoReflectionTypeBuilder *tb, MonoReflectionEventBuilder *eb)
+static MonoReflectionEvent *
+reflection_event_builder_get_event_info (MonoReflectionTypeBuilder *tb, MonoReflectionEventBuilder *eb, MonoError *error)
 {
-       MonoError error;
+       mono_error_init (error);
+
        MonoEvent *event = g_new0 (MonoEvent, 1);
        MonoClass *klass;
 
-       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)tb, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)tb, error);
+       if (!is_ok (error)) {
+               g_free (event);
+               return NULL;
+       }
        klass = mono_class_from_mono_type (type);
 
        event->parent = klass;
@@ -12809,11 +13053,26 @@ mono_reflection_event_builder_get_event_info (MonoReflectionTypeBuilder *tb, Mon
        }
 #endif
 
-       MonoReflectionEvent *ev_obj = mono_event_get_object_checked (mono_object_domain (tb), klass, event, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       MonoReflectionEvent *ev_obj = mono_event_get_object_checked (mono_object_domain (tb), klass, event, error);
+       if (!is_ok (error)) {
+#ifndef MONO_SMALL_CONFIG
+               g_free (event->other);
+#endif
+               g_free (event);
+               return NULL;
+       }
        return ev_obj;
 }
 
+MonoReflectionEvent *
+mono_reflection_event_builder_get_event_info (MonoReflectionTypeBuilder *tb, MonoReflectionEventBuilder *eb)
+{
+       MonoError error;
+       MonoReflectionEvent *result = reflection_event_builder_get_event_info (tb, eb, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
 static void
 typebuilder_setup_events (MonoClass *klass, MonoError *error)
 {
@@ -12863,16 +13122,34 @@ typebuilder_setup_events (MonoClass *klass, MonoError *error)
        }
 }
 
+struct remove_instantiations_user_data
+{
+       MonoClass *klass;
+       MonoError *error;
+};
+
 static gboolean
 remove_instantiations_of_and_ensure_contents (gpointer key,
                                                  gpointer value,
                                                  gpointer user_data)
 {
+       struct remove_instantiations_user_data *data = (struct remove_instantiations_user_data*)user_data;
        MonoType *type = (MonoType*)key;
-       MonoClass *klass = (MonoClass*)user_data;
+       MonoClass *klass = data->klass;
+       gboolean already_failed = !is_ok (data->error);
+       MonoError lerror;
+       MonoError *error = already_failed ? &lerror : data->error;
 
        if ((type->type == MONO_TYPE_GENERICINST) && (type->data.generic_class->container_class == klass)) {
-               fix_partial_generic_class (mono_class_from_mono_type (type)); //Ensure it's safe to use it.
+               MonoClass *inst_klass = mono_class_from_mono_type (type);
+               //Ensure it's safe to use it.
+               if (!fix_partial_generic_class (inst_klass, error)) {
+                       mono_class_set_failure (inst_klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
+                       // Marked the class with failure, but since some other instantiation already failed,
+                       // just report that one, and swallow the error from this one.
+                       if (already_failed)
+                               mono_error_cleanup (error);
+               }
                return TRUE;
        } else
                return FALSE;
@@ -12903,6 +13180,8 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
        MonoReflectionType* res;
        int i, j;
 
+       mono_error_init (&error);
+
        domain = mono_object_domain (tb);
        klass = mono_class_from_mono_type (tb->type.type);
 
@@ -12910,22 +13189,28 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
         * Check for user defined Type subclasses.
         */
        RESOLVE_TYPE (tb->parent, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error))
+               goto failure_unlocked;
        check_array_for_usertypes (tb->interfaces, &error);
-       mono_error_raise_exception (&error); /*FIXME don't raise here */
+       if (!is_ok (&error))
+               goto failure_unlocked;
        if (tb->fields) {
                for (i = 0; i < mono_array_length (tb->fields); ++i) {
                        MonoReflectionFieldBuilder *fb = (MonoReflectionFieldBuilder *)mono_array_get (tb->fields, gpointer, i);
                        if (fb) {
                                RESOLVE_TYPE (fb->type, &error);
-                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                check_array_for_usertypes (fb->modreq, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                check_array_for_usertypes (fb->modopt, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                if (fb->marshal_info && fb->marshal_info->marshaltyperef) {
                                        RESOLVE_TYPE (fb->marshal_info->marshaltyperef, &error);
-                                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                                       if (!is_ok (&error))
+                                               goto failure_unlocked;
                                }
                        }
                }
@@ -12935,22 +13220,28 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
                        MonoReflectionMethodBuilder *mb = (MonoReflectionMethodBuilder *)mono_array_get (tb->methods, gpointer, i);
                        if (mb) {
                                RESOLVE_TYPE (mb->rtype, &error);
-                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                check_array_for_usertypes (mb->return_modreq, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                check_array_for_usertypes (mb->return_modopt, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                check_array_for_usertypes (mb->parameters, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                if (mb->param_modreq)
                                        for (j = 0; j < mono_array_length (mb->param_modreq); ++j) {
                                                check_array_for_usertypes (mono_array_get (mb->param_modreq, MonoArray*, j), &error);
-                                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                                               if (!is_ok (&error))
+                                                       goto failure_unlocked;
                                        }
                                if (mb->param_modopt)
                                        for (j = 0; j < mono_array_length (mb->param_modopt); ++j) {
                                                check_array_for_usertypes (mono_array_get (mb->param_modopt, MonoArray*, j), &error);
-                                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                                               if (!is_ok (&error))
+                                                       goto failure_unlocked;
                                        }
                        }
                }
@@ -12960,16 +13251,19 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
                        MonoReflectionCtorBuilder *mb = (MonoReflectionCtorBuilder *)mono_array_get (tb->ctors, gpointer, i);
                        if (mb) {
                                check_array_for_usertypes (mb->parameters, &error);
-                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                               if (!is_ok (&error))
+                                       goto failure_unlocked;
                                if (mb->param_modreq)
                                        for (j = 0; j < mono_array_length (mb->param_modreq); ++j) {
                                                check_array_for_usertypes (mono_array_get (mb->param_modreq, MonoArray*, j), &error);
-                                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                                               if (!is_ok (&error))
+                                                       goto failure_unlocked;
                                        }
                                if (mb->param_modopt)
                                        for (j = 0; j < mono_array_length (mb->param_modopt); ++j) {
                                                check_array_for_usertypes (mono_array_get (mb->param_modopt, MonoArray*, j), &error);
-                                               mono_error_raise_exception (&error); /*FIXME don't raise here */
+                                               if (!is_ok (&error))
+                                                       goto failure_unlocked;
                                        }
                        }
                }
@@ -12988,7 +13282,7 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
                mono_loader_unlock ();
 
                res = mono_type_get_object_checked (mono_object_domain (tb), &klass->byval_arg, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_error_set_pending_exception (&error);
 
                return res;
        }
@@ -13016,7 +13310,7 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
                        mono_domain_unlock (domain);
 
                        res = mono_type_get_object_checked (mono_object_domain (tb), &klass->byval_arg, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_error_set_pending_exception (&error);
 
                        return res;
                }
@@ -13077,19 +13371,28 @@ mono_reflection_create_runtime_class (MonoReflectionTypeBuilder *tb)
         *
         * Together with this we must ensure the contents of all instances to match the created type.
         */
-       if (domain->type_hash && klass->generic_container)
-               mono_g_hash_table_foreach_remove (domain->type_hash, remove_instantiations_of_and_ensure_contents, klass);
+       if (domain->type_hash && klass->generic_container) {
+               struct remove_instantiations_user_data data;
+               data.klass = klass;
+               data.error = &error;
+               mono_error_assert_ok (&error);
+               mono_g_hash_table_foreach_remove (domain->type_hash, remove_instantiations_of_and_ensure_contents, &data);
+               if (!is_ok (&error))
+                       goto failure;
+       }
 
        mono_domain_unlock (domain);
        mono_loader_unlock ();
 
        if (klass->enumtype && !mono_class_is_valid_enum (klass)) {
                mono_class_set_failure (klass, MONO_EXCEPTION_TYPE_LOAD, NULL);
-               mono_raise_exception (mono_get_exception_type_load (tb->name, NULL));
+               mono_error_set_type_load_class (&error, klass, "Not a valid enumeration");
+               goto failure_unlocked;
        }
 
        res = mono_type_get_object_checked (mono_object_domain (tb), &klass->byval_arg, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error))
+               goto failure_unlocked;
 
        g_assert (res != (MonoReflectionType*)tb);
 
@@ -13100,30 +13403,32 @@ failure:
        klass->wastypebuilder = TRUE;
        mono_domain_unlock (domain);
        mono_loader_unlock ();
-       mono_error_raise_exception (&error);
+failure_unlocked:
+       mono_error_set_pending_exception (&error);
        return NULL;
 }
 
-void
-mono_reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam)
+static gboolean
+reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam, MonoError *error)
 {
        MonoGenericParamFull *param;
        MonoImage *image;
        MonoClass *pklass;
-       MonoError error;
+
+       mono_error_init (error);
 
        image = &gparam->tbuilder->module->dynamic_image->image;
 
        param = mono_image_new0 (image, MonoGenericParamFull, 1);
 
-       param->info.name = mono_string_to_utf8_image (image, gparam->name, &error);
-       g_assert (mono_error_ok (&error));
+       param->info.name = mono_string_to_utf8_image (image, gparam->name, error);
+       mono_error_assert_ok (error);
        param->param.num = gparam->index;
 
        if (gparam->mbuilder) {
                if (!gparam->mbuilder->generic_container) {
-                       MonoType *tb = mono_reflection_type_get_handle ((MonoReflectionType*)gparam->mbuilder->type, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *tb = mono_reflection_type_get_handle ((MonoReflectionType*)gparam->mbuilder->type, error);
+                       return_val_if_nok (error, FALSE);
 
                        MonoClass *klass = mono_class_from_mono_type (tb);
                        gparam->mbuilder->generic_container = (MonoGenericContainer *)mono_image_alloc0 (klass->image, sizeof (MonoGenericContainer));
@@ -13138,8 +13443,8 @@ mono_reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam
                param->param.owner = gparam->mbuilder->generic_container;
        } else if (gparam->tbuilder) {
                if (!gparam->tbuilder->generic_container) {
-                       MonoType *tb = mono_reflection_type_get_handle ((MonoReflectionType*)gparam->tbuilder, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *tb = mono_reflection_type_get_handle ((MonoReflectionType*)gparam->tbuilder, error);
+                       return_val_if_nok (error, FALSE);
                        MonoClass *klass = mono_class_from_mono_type (tb);
                        gparam->tbuilder->generic_container = (MonoGenericContainer *)mono_image_alloc0 (klass->image, sizeof (MonoGenericContainer));
                        gparam->tbuilder->generic_container->owner.klass = klass;
@@ -13153,12 +13458,22 @@ mono_reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam
 
        mono_class_set_ref_info (pklass, gparam);
        mono_image_append_class_to_reflection_info_set (pklass);
+
+       return TRUE;
 }
 
-MonoArray *
-mono_reflection_sighelper_get_signature_local (MonoReflectionSigHelper *sig)
+void
+mono_reflection_initialize_generic_parameter (MonoReflectionGenericParam *gparam)
 {
        MonoError error;
+       (void) reflection_initialize_generic_parameter (gparam, &error);
+       mono_error_set_pending_exception (&error);
+}
+
+
+static MonoArray *
+reflection_sighelper_get_signature_local (MonoReflectionSigHelper *sig, MonoError *error)
+{
        MonoReflectionModuleBuilder *module = sig->module;
        MonoDynamicImage *assembly = module != NULL ? module->dynamic_image : NULL;
        guint32 na = sig->arguments ? mono_array_length (sig->arguments) : 0;
@@ -13166,8 +13481,10 @@ mono_reflection_sighelper_get_signature_local (MonoReflectionSigHelper *sig)
        MonoArray *result;
        SigBuffer buf;
 
-       check_array_for_usertypes (sig->arguments, &error);
-       mono_error_raise_exception (&error); /* FIXME: don't raise here */
+       mono_error_init (error);
+
+       check_array_for_usertypes (sig->arguments, error);
+       return_val_if_nok (error, NULL);
 
        sigbuffer_init (&buf, 32);
 
@@ -13176,57 +13493,76 @@ mono_reflection_sighelper_get_signature_local (MonoReflectionSigHelper *sig)
        if (assembly != NULL){
                for (i = 0; i < na; ++i) {
                        MonoReflectionType *type = mono_array_get (sig->arguments, MonoReflectionType*, i);
-                       encode_reflection_type (assembly, type, &buf, &error);
-                       if (!is_ok (&error)) goto fail;
+                       encode_reflection_type (assembly, type, &buf, error);
+                       if (!is_ok (error)) goto fail;
                }
        }
 
        buflen = buf.p - buf.buf;
-       result = mono_array_new (mono_domain_get (), mono_defaults.byte_class, buflen);
+       result = mono_array_new_checked (mono_domain_get (), mono_defaults.byte_class, buflen, error);
+       if (!is_ok (error)) goto fail;
        memcpy (mono_array_addr (result, char, 0), buf.buf, buflen);
        sigbuffer_free (&buf);
        return result;
 fail:
        sigbuffer_free (&buf);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
        return NULL;
 }
 
 MonoArray *
-mono_reflection_sighelper_get_signature_field (MonoReflectionSigHelper *sig)
+mono_reflection_sighelper_get_signature_local (MonoReflectionSigHelper *sig)
 {
        MonoError error;
+       MonoArray *result = reflection_sighelper_get_signature_local (sig, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
+static MonoArray *
+reflection_sighelper_get_signature_field (MonoReflectionSigHelper *sig, MonoError *error)
+{
        MonoDynamicImage *assembly = sig->module->dynamic_image;
        guint32 na = sig->arguments ? mono_array_length (sig->arguments) : 0;
        guint32 buflen, i;
        MonoArray *result;
        SigBuffer buf;
 
-       check_array_for_usertypes (sig->arguments, &error);
-       mono_error_raise_exception (&error); /* FIXME: don't raise here */
+       mono_error_init (error);
+
+       check_array_for_usertypes (sig->arguments, error);
+       return_val_if_nok (error, NULL);
 
        sigbuffer_init (&buf, 32);
 
        sigbuffer_add_value (&buf, 0x06);
        for (i = 0; i < na; ++i) {
                MonoReflectionType *type = mono_array_get (sig->arguments, MonoReflectionType*, i);
-               encode_reflection_type (assembly, type, &buf, &error);
-               if (!is_ok (&error))
+               encode_reflection_type (assembly, type, &buf, error);
+               if (!is_ok (error))
                        goto fail;
        }
 
        buflen = buf.p - buf.buf;
-       result = mono_array_new (mono_domain_get (), mono_defaults.byte_class, buflen);
+       result = mono_array_new_checked (mono_domain_get (), mono_defaults.byte_class, buflen, error);
+       if (!is_ok (error)) goto fail;
        memcpy (mono_array_addr (result, char, 0), buf.buf, buflen);
        sigbuffer_free (&buf);
 
        return result;
 fail:
        sigbuffer_free (&buf);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
        return NULL;
 }
 
+MonoArray *
+mono_reflection_sighelper_get_signature_field (MonoReflectionSigHelper *sig)
+{
+       MonoError error;
+       MonoArray *result = reflection_sighelper_get_signature_field (sig, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
+}
+
 typedef struct {
        MonoMethod *handle;
        MonoDomain *domain;
@@ -13256,10 +13592,9 @@ free_dynamic_method (void *dynamic_method)
        g_free (data);
 }
 
-void 
-mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
+static gboolean
+reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb, MonoError *error)
 {
-       MonoError error;
        MonoReferenceQueue *queue;
        MonoMethod *handle;
        DynamicMethodReleaseData *release_data;
@@ -13270,8 +13605,12 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
        GSList *l;
        int i;
 
-       if (mono_runtime_is_shutting_down ())
-               mono_raise_exception (mono_get_exception_invalid_operation (""));
+       mono_error_init (error);
+
+       if (mono_runtime_is_shutting_down ()) {
+               mono_error_set_generic_error (error, "System", "InvalidOperationException", "");
+               return FALSE;
+       }
 
        if (!(queue = dynamic_method_queue)) {
                mono_loader_lock ();
@@ -13280,7 +13619,8 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
                mono_loader_unlock ();
        }
 
-       sig = dynamic_method_to_signature (mb);
+       sig = dynamic_method_to_signature (mb, error);
+       return_val_if_nok (error, FALSE);
 
        reflection_methodbuilder_from_dynamic_method (&rmb, mb);
 
@@ -13318,7 +13658,11 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
                        handle_class = mono_defaults.methodhandle_class;
                } else {
                        MonoException *ex = NULL;
-                       ref = resolve_object (mb->module->image, obj, &handle_class, NULL);
+                       ref = resolve_object (mb->module->image, obj, &handle_class, NULL, error);
+                       if (!is_ok  (error)) {
+                               g_free (rmb.refs);
+                               return FALSE;
+                       }
                        if (!ref)
                                ex = mono_get_exception_type_load (NULL, NULL);
                        else if (mono_security_core_clr_enabled ())
@@ -13326,8 +13670,8 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
 
                        if (ex) {
                                g_free (rmb.refs);
-                               mono_raise_exception (ex);
-                               return;
+                               mono_error_set_exception_instance (error, ex);
+                               return FALSE;
                        }
                }
 
@@ -13336,17 +13680,20 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
        }               
 
        if (mb->owner) {
-               MonoType *owner_type = mono_reflection_type_get_handle ((MonoReflectionType*)mb->owner, &error);
-               if (!is_ok (&error)) {
+               MonoType *owner_type = mono_reflection_type_get_handle ((MonoReflectionType*)mb->owner, error);
+               if (!is_ok (error)) {
                        g_free (rmb.refs);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       return FALSE;
                }
                klass = mono_class_from_mono_type (owner_type);
        } else {
                klass = mono_defaults.object_class;
        }
 
-       mb->mhandle = handle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig);
+       mb->mhandle = handle = reflection_methodbuilder_to_mono_method (klass, &rmb, sig, error);
+       g_free (rmb.refs);
+       return_val_if_nok (error, FALSE);
+
        release_data = g_new (DynamicMethodReleaseData, 1);
        release_data->handle = handle;
        release_data->domain = mono_object_get_domain ((MonoObject*)mb);
@@ -13369,8 +13716,6 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
        }
        g_slist_free (mb->referenced_by);
 
-       g_free (rmb.refs);
-
        /* ilgen is no longer needed */
        mb->ilgen = NULL;
 
@@ -13380,6 +13725,16 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
                domain->method_to_dyn_method = g_hash_table_new (NULL, NULL);
        g_hash_table_insert (domain->method_to_dyn_method, handle, (gpointer)(size_t)mono_gchandle_new_weakref ((MonoObject *)mb, TRUE));
        mono_domain_unlock (domain);
+
+       return TRUE;
+}
+
+void
+mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
+{
+       MonoError error;
+       (void) reflection_create_dynamic_method (mb, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 #endif /* DISABLE_REFLECTION_EMIT */
@@ -13425,23 +13780,28 @@ mono_reflection_lookup_signature (MonoImage *image, MonoMethod *method, guint32
  * LOCKING: Take the loader lock
  */
 gpointer
-mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context)
+mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context, MonoError *error)
 {
        MonoDynamicImage *assembly = (MonoDynamicImage*)image;
        MonoObject *obj;
        MonoClass *klass;
 
+       mono_error_init (error);
+       
        obj = lookup_dyn_token (assembly, token);
        if (!obj) {
                if (valid_token)
                        g_error ("Could not find required dynamic token 0x%08x", token);
-               else
+               else {
+                       mono_error_set_execution_engine (error, "Could not find dynamic token 0x%08x", token);
                        return NULL;
+               }
        }
 
        if (!handle_class)
                handle_class = &klass;
-       return resolve_object (image, obj, handle_class, context);
+       gpointer result = resolve_object (image, obj, handle_class, context, error);
+       return result;
 }
 
 /*
@@ -13451,15 +13811,15 @@ mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean
  * dynamic types.
  */
 static void
-ensure_complete_type (MonoClass *klass)
+ensure_complete_type (MonoClass *klass, MonoError *error)
 {
-       MonoError error;
+       mono_error_init (error);
 
        if (image_is_dynamic (klass->image) && !klass->wastypebuilder && mono_class_get_ref_info (klass)) {
                MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder *)mono_class_get_ref_info (klass);
 
-               mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, error);
+               return_if_nok (error);
 
                // Asserting here could break a lot of code
                //g_assert (klass->wastypebuilder);
@@ -13470,32 +13830,36 @@ ensure_complete_type (MonoClass *klass)
                int i;
 
                for (i = 0; i < inst->type_argc; ++i) {
-                       ensure_complete_type (mono_class_from_mono_type (inst->type_argv [i]));
+                       ensure_complete_type (mono_class_from_mono_type (inst->type_argv [i]), error);
+                       return_if_nok (error);
                }
        }
 }
 
 static gpointer
-resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, MonoGenericContext *context)
+resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, MonoGenericContext *context, MonoError *error)
 {
-       MonoError error;
        gpointer result = NULL;
 
+       mono_error_init (error);
+
        if (strcmp (obj->vtable->klass->name, "String") == 0) {
-               result = mono_string_intern_checked ((MonoString*)obj, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               result = mono_string_intern_checked ((MonoString*)obj, error);
+               return_val_if_nok (error, NULL);
                *handle_class = mono_defaults.string_class;
                g_assert (result);
        } else if (strcmp (obj->vtable->klass->name, "MonoType") == 0) {
-               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, error);
+               return_val_if_nok (error, NULL);
                MonoClass *mc = mono_class_from_mono_type (type);
-               if (!mono_class_init (mc))
-                       mono_raise_exception (mono_class_get_exception_for_failure (mc));
+               if (!mono_class_init (mc)) {
+                       mono_error_set_exception_instance (error, mono_class_get_exception_for_failure (mc));
+                       return NULL;
+               }
 
                if (context) {
-                       MonoType *inflated = mono_class_inflate_generic_type_checked (type, context, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *inflated = mono_class_inflate_generic_type_checked (type, context, error);
+                       return_val_if_nok (error, NULL);
 
                        result = mono_class_from_mono_type (inflated);
                        mono_metadata_free_type (inflated);
@@ -13510,9 +13874,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                   strcmp (obj->vtable->klass->name, "MonoGenericMethod") == 0) {
                result = ((MonoReflectionMethod*)obj)->method;
                if (context) {
-                       MonoError error;
-                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, &error);
-                       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, error);
+                       mono_error_assert_ok (error);
                }
                *handle_class = mono_defaults.methodhandle_class;
                g_assert (result);
@@ -13523,8 +13886,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                        /* Type is not yet created */
                        MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder*)mb->type;
 
-                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, error);
+                       return_val_if_nok (error, NULL);
 
                        /*
                         * Hopefully this has been filled in by calling CreateType() on the
@@ -13537,9 +13900,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                        result = mb->mhandle;
                }
                if (context) {
-                       MonoError error;
-                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, &error);
-                       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, error);
+                       mono_error_assert_ok (error);
                }
                *handle_class = mono_defaults.methodhandle_class;
        } else if (strcmp (obj->vtable->klass->name, "ConstructorBuilder") == 0) {
@@ -13549,23 +13911,24 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                if (!result) {
                        MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder*)cb->type;
 
-                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, error);
+                       return_val_if_nok (error, NULL);
                        result = cb->mhandle;
                }
                if (context) {
-                       MonoError error;
-                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, &error);
-                       g_assert (mono_error_ok (&error)); /* FIXME don't swallow the error */
+                       result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, error);
+                       mono_error_assert_ok (error);
                }
                *handle_class = mono_defaults.methodhandle_class;
        } else if (strcmp (obj->vtable->klass->name, "MonoField") == 0) {
                MonoClassField *field = ((MonoReflectionField*)obj)->field;
 
-               ensure_complete_type (field->parent);
+               ensure_complete_type (field->parent, error);
+               return_val_if_nok (error, NULL);
+
                if (context) {
-                       MonoType *inflated = mono_class_inflate_generic_type_checked (&field->parent->byval_arg, context, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *inflated = mono_class_inflate_generic_type_checked (&field->parent->byval_arg, context, error);
+                       return_val_if_nok (error, NULL);
 
                        MonoClass *klass = mono_class_from_mono_type (inflated);
                        MonoClassField *inflated_field;
@@ -13589,15 +13952,15 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                if (!result) {
                        MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder*)fb->typeb;
 
-                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, error);
+                       return_val_if_nok (error, NULL);
                        result = fb->handle;
                }
 
                if (fb->handle && fb->handle->parent->generic_container) {
                        MonoClass *klass = fb->handle->parent;
-                       MonoType *type = mono_class_inflate_generic_type_checked (&klass->byval_arg, context, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *type = mono_class_inflate_generic_type_checked (&klass->byval_arg, context, error);
+                       return_val_if_nok (error, NULL);
 
                        MonoClass *inflated = mono_class_from_mono_type (type);
 
@@ -13608,8 +13971,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                *handle_class = mono_defaults.fieldhandle_class;
        } else if (strcmp (obj->vtable->klass->name, "TypeBuilder") == 0) {
                MonoReflectionTypeBuilder *tb = (MonoReflectionTypeBuilder*)obj;
-               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)tb, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)tb, error);
+               return_val_if_nok (error, NULL);
                MonoClass *klass;
 
                klass = type->data.klass;
@@ -13618,8 +13981,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                        result = klass;
                }
                else {
-                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_domain_try_type_resolve_checked (mono_domain_get (), NULL, (MonoObject*)tb, error);
+                       return_val_if_nok (error, NULL);
                        result = type->data.klass;
                        g_assert (result);
                }
@@ -13651,8 +14014,11 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                /* TODO: Copy type ? */
                sig->ret = helper->return_type->type;
                for (i = 0; i < nargs; ++i) {
-                       sig->params [i] = mono_type_array_get_and_resolve (helper->arguments, i, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       sig->params [i] = mono_type_array_get_and_resolve (helper->arguments, i, error);
+                       if (!is_ok (error)) {
+                               image_g_free (image, sig);
+                               return NULL;
+                       }
                }
 
                result = sig;
@@ -13664,20 +14030,20 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                result = method->mhandle;
                *handle_class = mono_defaults.methodhandle_class;
        } else if (strcmp (obj->vtable->klass->name, "GenericTypeParameterBuilder") == 0) {
-               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
-               type = mono_class_inflate_generic_type_checked (type, context, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, error);
+               return_val_if_nok (error, NULL);
+               type = mono_class_inflate_generic_type_checked (type, context, error);
+               return_val_if_nok (error, NULL);
 
                result = mono_class_from_mono_type (type);
                *handle_class = mono_defaults.typehandle_class;
                g_assert (result);
                mono_metadata_free_type (type);
        } else if (strcmp (obj->vtable->klass->name, "MonoGenericClass") == 0) {
-               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
-               type = mono_class_inflate_generic_type_checked (type, context, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *type = mono_reflection_type_get_handle ((MonoReflectionType*)obj, error);
+               return_val_if_nok (error, NULL);
+               type = mono_class_inflate_generic_type_checked (type, context, error);
+               return_val_if_nok (error, NULL);
 
                result = mono_class_from_mono_type (type);
                *handle_class = mono_defaults.typehandle_class;
@@ -13696,24 +14062,29 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                else
                        g_error ("resolve_object:: can't handle a FTBI with base_method of type %s", mono_type_get_full_name (mono_object_class (f->fb)));
 
-               MonoType *finst = mono_reflection_type_get_handle ((MonoReflectionType*)f->inst, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
-               type = mono_class_inflate_generic_type_checked (finst, context, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *finst = mono_reflection_type_get_handle ((MonoReflectionType*)f->inst, error);
+               return_val_if_nok (error, NULL);
+               type = mono_class_inflate_generic_type_checked (finst, context, error);
+               return_val_if_nok (error, NULL);
 
                inflated = mono_class_from_mono_type (type);
 
                result = field = mono_class_get_field_from_name (inflated, mono_field_get_name (field));
-               ensure_complete_type (field->parent);
+               ensure_complete_type (field->parent, error);
+               if (!is_ok (error)) {
+                       mono_metadata_free_type (type);
+                       return NULL;
+               }
+
                g_assert (result);
                mono_metadata_free_type (type);
                *handle_class = mono_defaults.fieldhandle_class;
        } else if (strcmp (obj->vtable->klass->name, "ConstructorOnTypeBuilderInst") == 0) {
                MonoReflectionCtorOnTypeBuilderInst *c = (MonoReflectionCtorOnTypeBuilderInst*)obj;
-               MonoType *cinst = mono_reflection_type_get_handle ((MonoReflectionType*)c->inst, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
-               MonoType *type = mono_class_inflate_generic_type_checked (cinst, context, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *cinst = mono_reflection_type_get_handle ((MonoReflectionType*)c->inst, error);
+               return_val_if_nok (error, NULL);
+               MonoType *type = mono_class_inflate_generic_type_checked (cinst, context, error);
+               return_val_if_nok (error, NULL);
 
                MonoClass *inflated_klass = mono_class_from_mono_type (type);
                MonoMethod *method;
@@ -13731,17 +14102,17 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
        } else if (strcmp (obj->vtable->klass->name, "MethodOnTypeBuilderInst") == 0) {
                MonoReflectionMethodOnTypeBuilderInst *m = (MonoReflectionMethodOnTypeBuilderInst*)obj;
                if (m->method_args) {
-                       result = mono_reflection_method_on_tb_inst_get_handle (m, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       result = mono_reflection_method_on_tb_inst_get_handle (m, error);
+                       return_val_if_nok (error, NULL);
                        if (context) {
-                               result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, &error);
-                               mono_error_assert_ok (&error);
+                               result = mono_class_inflate_generic_method_checked ((MonoMethod *)result, context, error);
+                               mono_error_assert_ok (error);
                        }
                } else {
-                       MonoType *minst = mono_reflection_type_get_handle ((MonoReflectionType*)m->inst, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
-                       MonoType *type = mono_class_inflate_generic_type_checked (minst, context, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *minst = mono_reflection_type_get_handle ((MonoReflectionType*)m->inst, error);
+                       return_val_if_nok (error, NULL);
+                       MonoType *type = mono_class_inflate_generic_type_checked (minst, context, error);
+                       return_val_if_nok (error, NULL);
 
                        MonoClass *inflated_klass = mono_class_from_mono_type (type);
                        MonoMethod *method;
@@ -13765,8 +14136,8 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                gpointer iter;
                char *name;
 
-               mtype = mono_reflection_type_get_handle (m->parent, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mtype = mono_reflection_type_get_handle (m->parent, error);
+               return_val_if_nok (error, NULL);
                klass = mono_class_from_mono_type (mtype);
 
                /* Find the method */
@@ -13789,12 +14160,12 @@ resolve_object (MonoImage *image, MonoObject *obj, MonoClass **handle_class, Mon
                                is_sre_byref (mono_object_get_class(obj)) ||
                                is_sre_pointer (mono_object_get_class(obj))) {
                MonoReflectionType *ref_type = (MonoReflectionType *)obj;
-               MonoType *type = mono_reflection_type_get_handle (ref_type, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               MonoType *type = mono_reflection_type_get_handle (ref_type, error);
+               return_val_if_nok (error, NULL);
 
                if (context) {
-                       MonoType *inflated = mono_class_inflate_generic_type_checked (type, context, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MonoType *inflated = mono_class_inflate_generic_type_checked (type, context, error);
+                       return_val_if_nok (error, NULL);
 
                        result = mono_class_from_mono_type (inflated);
                        mono_metadata_free_type (inflated);
@@ -13830,10 +14201,11 @@ mono_reflection_setup_generic_class (MonoReflectionTypeBuilder *tb)
        g_assert_not_reached ();
 }
 
-void
-mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb)
+gboolean
+mono_reflection_create_generic_class (MonoReflectionTypeBuilder *tb, MonoError *error)
 {
        g_assert_not_reached ();
+       return FALSE;
 }
 
 void
@@ -13901,8 +14273,9 @@ mono_reflection_generic_class_initialize (MonoReflectionGenericClass *type, Mono
 }
 
 void
-mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides)
+mono_reflection_get_dynamic_overrides (MonoClass *klass, MonoMethod ***overrides, int *num_overrides, MonoError *error)
 {
+       mono_error_init (error);
        *overrides = NULL;
        *num_overrides = 0;
 }
@@ -13947,8 +14320,9 @@ mono_reflection_create_dynamic_method (MonoReflectionDynamicMethod *mb)
 }
 
 gpointer
-mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context)
+mono_reflection_lookup_dynamic_token (MonoImage *image, guint32 token, gboolean valid_token, MonoClass **handle_class, MonoGenericContext *context, MonoError *error)
 {
+       mono_error_init (error);
        return NULL;
 }
 
@@ -14395,13 +14769,14 @@ mono_declsec_get_assembly_action (MonoAssembly *assembly, guint32 action, MonoDe
 }
 
 gboolean
-mono_reflection_call_is_assignable_to (MonoClass *klass, MonoClass *oklass)
+mono_reflection_call_is_assignable_to (MonoClass *klass, MonoClass *oklass, MonoError *error)
 {
-       MonoError error;
        MonoObject *res, *exc;
        void *params [1];
        static MonoMethod *method = NULL;
 
+       mono_error_init (error);
+
        if (method == NULL) {
                method = mono_class_get_method_from_name (mono_class_get_type_builder_class (), "IsAssignableTo", 1);
                g_assert (method);
@@ -14414,13 +14789,13 @@ mono_reflection_call_is_assignable_to (MonoClass *klass, MonoClass *oklass)
        g_assert (mono_class_get_ref_info (klass));
        g_assert (!strcmp (((MonoObject*)(mono_class_get_ref_info (klass)))->vtable->klass->name, "TypeBuilder"));
 
-       params [0] = mono_type_get_object_checked (mono_domain_get (), &oklass->byval_arg, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       params [0] = mono_type_get_object_checked (mono_domain_get (), &oklass->byval_arg, error);
+       return_val_if_nok (error, FALSE);
 
-       res = mono_runtime_try_invoke (method, (MonoObject*)(mono_class_get_ref_info (klass)), params, &exc, &error);
+       res = mono_runtime_try_invoke (method, (MonoObject*)(mono_class_get_ref_info (klass)), params, &exc, error);
 
-       if (exc || !mono_error_ok (&error)) {
-               mono_error_cleanup (&error);
+       if (exc || !mono_error_ok (error)) {
+               mono_error_cleanup (error);
                return FALSE;
        } else
                return *(MonoBoolean*)mono_object_unbox (res);
index 164cc4ae87cfe996d18bbeabdea99255c6ca867c..ad28290bcc93a30e979f7e7d7cc3b1e09e8fafb4 100644 (file)
@@ -1,6 +1,7 @@
 #ifndef __METADATA_REFLECTION_H__
 #define __METADATA_REFLECTION_H__
 
+#include <mono/utils/mono-compiler.h>
 #include <mono/metadata/object.h>
 
 MONO_BEGIN_DECLS
@@ -77,6 +78,7 @@ MONO_API MonoArray*  mono_reflection_get_custom_attrs_by_type (MonoObject *obj,
 MONO_API MonoArray*  mono_reflection_get_custom_attrs (MonoObject *obj);
 MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*  mono_reflection_get_custom_attrs_data (MonoObject *obj);
+MONO_RT_EXTERNAL_ONLY
 MONO_API MonoArray*  mono_reflection_get_custom_attrs_blob (MonoReflectionAssembly *assembly, MonoObject *ctor, MonoArray *ctorArgs, MonoArray *properties, MonoArray *porpValues, MonoArray *fields, MonoArray* fieldValues);
 
 MONO_RT_EXTERNAL_ONLY
index 9b621c92fc577f1ec9e486e9f7fe2e8db2cfd4d3..2b1a9d6b1949a31bf130d234779c79b43eee4102 100644 (file)
@@ -5,6 +5,7 @@
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011-2014 Xamarin, Inc (http://www.xamarin.com)
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -193,6 +194,9 @@ mono_remoting_marshal_init (void)
                register_icall (mono_marshal_xdomain_copy_out_value, "mono_marshal_xdomain_copy_out_value", "void object object", FALSE);
                register_icall (mono_remoting_wrapper, "mono_remoting_wrapper", "object ptr ptr", FALSE);
                register_icall (mono_upgrade_remote_class_wrapper, "mono_upgrade_remote_class_wrapper", "void object object", FALSE);
+               /* mono_load_remote_field_new_icall registered  by mini-runtime.c */
+               /* mono_store_remote_field_new_icall registered  by mini-runtime.c */
+
        }
 
        icalls_registered = TRUE;
@@ -373,9 +377,11 @@ mono_remoting_wrapper (MonoMethod *method, gpointer *params)
                                        mparams[i] = *((gpointer *)params [i]);
                                } else {
                                        /* runtime_invoke expects a boxed instance */
-                                       if (mono_class_is_nullable (mono_class_from_mono_type (sig->params [i])))
-                                               mparams[i] = mono_nullable_box ((guint8 *)params [i], klass);
-                                       else
+                                       if (mono_class_is_nullable (mono_class_from_mono_type (sig->params [i]))) {
+                                               mparams[i] = mono_nullable_box ((guint8 *)params [i], klass, &error);
+                                               if (!is_ok (&error))
+                                                       goto fail;
+                                       } else
                                                mparams[i] = params [i];
                                }
                        } else {
@@ -384,7 +390,8 @@ mono_remoting_wrapper (MonoMethod *method, gpointer *params)
                }
 
                res = mono_runtime_invoke_checked (method, method->klass->valuetype? mono_object_unbox ((MonoObject*)this_obj): this_obj, mparams, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               if (!is_ok (&error))
+                       goto fail;
 
                return res;
        }
@@ -392,16 +399,31 @@ mono_remoting_wrapper (MonoMethod *method, gpointer *params)
        msg = mono_method_call_message_new (method, params, NULL, NULL, NULL);
 
        res = mono_remoting_invoke ((MonoObject *)this_obj->rp, msg, &exc, &out_args, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       if (!is_ok (&error))
+               goto fail;
 
-       if (exc)
-               mono_raise_exception ((MonoException *)exc);
+       if (exc) {
+               mono_error_init (&error);
+               mono_error_set_exception_instance (&error, (MonoException *)exc);
+               goto fail;
+       }
 
-       mono_method_return_message_restore (method, params, out_args);
+       mono_method_return_message_restore (method, params, out_args, &error);
+       if (!is_ok (&error)) goto fail;
 
        return res;
+fail:
+       /* This icall will be called from managed code, and more over
+        * from a protected wrapper so interruptions such as pending
+        * exceptions will not be honored.  (See
+        * is_running_protected_wrapper () in threads.c and
+        * mono_marshal_get_remoting_invoke () in remoting.c)
+        */
+       mono_error_raise_exception (&error);
+       return NULL;
 } 
 
+
 MonoMethod *
 mono_marshal_get_remoting_invoke (MonoMethod *method)
 {
@@ -449,6 +471,11 @@ mono_marshal_get_remoting_invoke (MonoMethod *method)
        mono_mb_emit_ptr (mb, method);
        mono_mb_emit_ldloc (mb, params_var);
        mono_mb_emit_icall (mb, mono_remoting_wrapper);
+       // FIXME: this interrupt checkpoint code is a no-op since 'mb'
+       //  is a MONO_WRAPPER_REMOTING_INVOKE, and
+       //  mono_thread_interruption_checkpoint_request (FALSE)
+       //  considers such wrappers "protected" and always returns
+       //  NULL as if there's no pending interruption.
        mono_marshal_emit_thread_interrupt_checkpoint (mb);
 
        if (sig->ret->type == MONO_TYPE_VOID) {
@@ -532,8 +559,10 @@ mono_marshal_set_domain_by_id (gint32 id, MonoBoolean push)
        MonoDomain *current_domain = mono_domain_get ();
        MonoDomain *domain = mono_domain_get_by_id (id);
 
-       if (!domain || !mono_domain_set (domain, FALSE))        
-               mono_raise_exception (mono_get_exception_appdomain_unloaded ());
+       if (!domain || !mono_domain_set (domain, FALSE)) {
+               mono_set_pending_exception (mono_get_exception_appdomain_unloaded ());
+               return 0;
+       }
 
        if (push)
                mono_thread_push_appdomain_ref (domain);
@@ -1283,7 +1312,7 @@ mono_marshal_get_remoting_invoke_with_check (MonoMethod *method)
 MonoMethod *
 mono_marshal_get_ldfld_remote_wrapper (MonoClass *klass)
 {
-       MonoMethodSignature *sig, *csig;
+       MonoMethodSignature *sig;
        MonoMethodBuilder *mb;
        MonoMethod *res;
        static MonoMethod* cached = NULL;
@@ -1310,15 +1339,7 @@ mono_marshal_get_ldfld_remote_wrapper (MonoClass *klass)
        mono_mb_emit_ldarg (mb, 1);
        mono_mb_emit_ldarg (mb, 2);
 
-       csig = mono_metadata_signature_alloc (mono_defaults.corlib, 3);
-       csig->params [0] = &mono_defaults.object_class->byval_arg;
-       csig->params [1] = &mono_defaults.int_class->byval_arg;
-       csig->params [2] = &mono_defaults.int_class->byval_arg;
-       csig->ret = &mono_defaults.object_class->byval_arg;
-       csig->pinvoke = 1;
-
-       mono_mb_emit_native_call (mb, csig, mono_load_remote_field_new);
-       mono_marshal_emit_thread_interrupt_checkpoint (mb);
+       mono_mb_emit_icall (mb, mono_load_remote_field_new_icall);
 
        mono_mb_emit_byte (mb, CEE_RET);
 #endif
@@ -1641,7 +1662,7 @@ mono_marshal_get_ldflda_wrapper (MonoType *type)
 MonoMethod *
 mono_marshal_get_stfld_remote_wrapper (MonoClass *klass)
 {
-       MonoMethodSignature *sig, *csig;
+       MonoMethodSignature *sig;
        MonoMethodBuilder *mb;
        MonoMethod *res;
        static MonoMethod *cached = NULL;
@@ -1670,16 +1691,7 @@ mono_marshal_get_stfld_remote_wrapper (MonoClass *klass)
        mono_mb_emit_ldarg (mb, 2);
        mono_mb_emit_ldarg (mb, 3);
 
-       csig = mono_metadata_signature_alloc (mono_defaults.corlib, 4);
-       csig->params [0] = &mono_defaults.object_class->byval_arg;
-       csig->params [1] = &mono_defaults.int_class->byval_arg;
-       csig->params [2] = &mono_defaults.int_class->byval_arg;
-       csig->params [3] = &mono_defaults.object_class->byval_arg;
-       csig->ret = &mono_defaults.void_class->byval_arg;
-       csig->pinvoke = 1;
-
-       mono_mb_emit_native_call (mb, csig, mono_store_remote_field_new);
-       mono_marshal_emit_thread_interrupt_checkpoint (mb);
+       mono_mb_emit_icall (mb, mono_store_remote_field_new_icall);
 
        mono_mb_emit_byte (mb, CEE_RET);
 #endif
@@ -2009,7 +2021,10 @@ mono_marshal_xdomain_copy_value (MonoObject *val)
        case MONO_TYPE_U8:
        case MONO_TYPE_R4:
        case MONO_TYPE_R8: {
-               return mono_value_box (domain, mono_object_class (val), ((char*)val) + sizeof(MonoObject));
+               MonoObject *res = mono_value_box_checked (domain, mono_object_class (val), ((char*)val) + sizeof(MonoObject), &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               return res;
+
        }
        case MONO_TYPE_STRING: {
                MonoString *str = (MonoString *) val;
@@ -2023,7 +2038,9 @@ mono_marshal_xdomain_copy_value (MonoObject *val)
                MonoArray *acopy;
                MonoXDomainMarshalType mt = mono_get_xdomain_marshal_type (&(mono_object_class (val)->element_class->byval_arg));
                if (mt == MONO_MARSHAL_SERIALIZE) return NULL;
-               acopy = mono_array_clone_in_domain (domain, (MonoArray *) val);
+               acopy = mono_array_clone_in_domain (domain, (MonoArray *) val, &error);
+               mono_error_raise_exception (&error); /* FIXME don't raise here */
+
                if (mt == MONO_MARSHAL_COPY) {
                        int i, len = mono_array_length (acopy);
                        for (i = 0; i < len; i++) {
index fcd8782387635f0b44c57b60da57e779ab257c4c..1c41c797db4fa2c235cd84398bf04cdf7f45541b 100644 (file)
@@ -5,6 +5,7 @@
  *  Jonathan Pryor 
  *
  * Copyright 2010 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index fc2169f9131cbb25ad67e5c214c1863b997d8787..3fe3ac04867adab1867989d2365fc0a644e5e930 100644 (file)
@@ -6,6 +6,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright 2007-2010 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <mono/metadata/class-internals.h>
@@ -624,34 +625,38 @@ get_method_access_exception (const char *format, MonoMethod *caller, MonoMethod
  *     Transparent code cannot access to Critical fields and can only use
  *     them if they are visible from it's point of view.
  *
- *     A FieldAccessException is thrown if the field is cannot be accessed.
+ *     Returns TRUE if acess is allowed.  Otherwise returns FALSE and sets @error to a FieldAccessException if the field is cannot be accessed.
  */
-void
-mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field)
+gboolean
+mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field, MonoError *error)
 {
+       mono_error_init (error);
        MonoMethod *caller = get_reflection_caller ();
        /* CoreCLR restrictions applies to Transparent code/caller */
        if (mono_security_core_clr_method_level (caller, TRUE) != MONO_SECURITY_CORE_CLR_TRANSPARENT)
-               return;
+               return TRUE;
 
        if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_REFLECTION) {
                if (!mono_security_core_clr_is_platform_image (mono_field_get_parent(field)->image))
-                       return;
+                       return TRUE;
        }
 
        /* Transparent code cannot [get|set]value on Critical fields */
        if (mono_security_core_clr_class_level (mono_field_get_parent (field)) == MONO_SECURITY_CORE_CLR_CRITICAL) {
-               mono_raise_exception (get_field_access_exception (
+               mono_error_set_exception_instance (error, get_field_access_exception (
                        "Transparent method %s cannot get or set Critical field %s.", 
                        caller, field));
+               return FALSE;
        }
 
        /* also it cannot access a fields that is not visible from it's (caller) point of view */
        if (!check_field_access (caller, field)) {
-               mono_raise_exception (get_field_access_exception (
+               mono_error_set_exception_instance (error, get_field_access_exception (
                        "Transparent method %s cannot get or set private/internal field %s.", 
                        caller, field));
+               return FALSE;
        }
+       return TRUE;
 }
 
 /*
@@ -661,34 +666,38 @@ mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field)
  *     Transparent code cannot call Critical methods and can only call them
  *     if they are visible from it's point of view.
  *
- *     A MethodAccessException is thrown if the field is cannot be accessed.
+ *     If access is allowed returns TRUE.  Returns FALSE and sets @error to a MethodAccessException if the field is cannot be accessed.
  */
-void
-mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method)
+gboolean
+mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method, MonoError *error)
 {
+       mono_error_init (error);
        MonoMethod *caller = get_reflection_caller ();
        /* CoreCLR restrictions applies to Transparent code/caller */
        if (mono_security_core_clr_method_level (caller, TRUE) != MONO_SECURITY_CORE_CLR_TRANSPARENT)
-               return;
+               return TRUE;
 
        if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_REFLECTION) {
                if (!mono_security_core_clr_is_platform_image (method->klass->image))
-                       return;
+                       return TRUE;
        }
 
        /* Transparent code cannot invoke, even using reflection, Critical code */
        if (mono_security_core_clr_method_level (method, TRUE) == MONO_SECURITY_CORE_CLR_CRITICAL) {
-               mono_raise_exception (get_method_access_exception (
+               mono_error_set_exception_instance (error, get_method_access_exception (
                        "Transparent method %s cannot invoke Critical method %s.", 
                        caller, method));
+               return FALSE;
        }
 
        /* also it cannot invoke a method that is not visible from it's (caller) point of view */
        if (!check_method_access (caller, method)) {
-               mono_raise_exception (get_method_access_exception (
+               mono_error_set_exception_instance (error, get_method_access_exception (
                        "Transparent method %s cannot invoke private/internal method %s.", 
                        caller, method));
+               return FALSE;
        }
+       return TRUE;
 }
 
 /*
@@ -726,19 +735,20 @@ can_avoid_corlib_reflection_delegate_optimization (MonoMethod *method)
 /*
  * mono_security_core_clr_ensure_delegate_creation:
  *
- *     Return TRUE if a delegate can be created on the specified method. 
- *     CoreCLR also affect the binding, so throwOnBindFailure must be 
- *     FALSE to let this function return (FALSE) normally, otherwise (if
- *     throwOnBindFailure is TRUE) it will throw an ArgumentException.
+ *     Return TRUE if a delegate can be created on the specified
+ *     method.  CoreCLR can also affect the binding, this function may
+ *     return (FALSE) and set @error to an ArgumentException.
  *
- *     A MethodAccessException is thrown if the specified method is not
+ *     @error is set to a MethodAccessException if the specified method is not
  *     visible from the caller point of view.
  */
 gboolean
-mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean throwOnBindFailure)
+mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, MonoError *error)
 {
        MonoMethod *caller;
 
+       mono_error_init (error);
+
        /* note: mscorlib creates delegates to avoid reflection (optimization), we ignore those cases */
        if (can_avoid_corlib_reflection_delegate_optimization (method))
                return TRUE;
@@ -750,13 +760,10 @@ mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean th
 
        /* otherwise it (as a Transparent caller) cannot create a delegate on a Critical method... */
        if (mono_security_core_clr_method_level (method, TRUE) == MONO_SECURITY_CORE_CLR_CRITICAL) {
-               /* but this throws only if 'throwOnBindFailure' is TRUE */
-               if (!throwOnBindFailure)
-                       return FALSE;
-
-               mono_raise_exception (get_argument_exception (
+               mono_error_set_exception_instance (error, get_argument_exception (
                        "Transparent method %s cannot create a delegate on Critical method %s.", 
                        caller, method));
+               return FALSE;
        }
 
        if (mono_security_core_clr_get_options () & MONO_SECURITY_CORE_CLR_OPTIONS_RELAX_DELEGATE) {
@@ -766,9 +773,10 @@ mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean th
 
        /* also it cannot create the delegate on a method that is not visible from it's (caller) point of view */
        if (!check_method_access (caller, method)) {
-               mono_raise_exception (get_method_access_exception (
+               mono_error_set_exception_instance (error, get_method_access_exception (
                        "Transparent method %s cannot create a delegate on private/internal method %s.", 
                        caller, method));
+               return FALSE;
        }
 
        return TRUE;
@@ -1049,19 +1057,24 @@ mono_security_core_clr_require_elevated_permissions (void)
        return FALSE;
 }
 
-void
-mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field)
+gboolean
+mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field, MonoError *error)
 {
+       mono_error_init (error);
+       return TRUE;
 }
 
-void
-mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method)
+gboolean
+mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method, MonoError *error)
 {
+       mono_error_init (error);
+       return TRUE;
 }
 
 gboolean
-mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean throwOnBindFailure)
+mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, MonoError *error)
 {
+       mono_error_init (error);
        return TRUE;
 }
 
index ec2ab01ee264bf77f4e957bae389ab924783831e..51fdb8c1239eedc47904a1389ce8c3e92b69daaf 100644 (file)
@@ -42,9 +42,11 @@ extern gboolean mono_security_core_clr_test;
 extern void mono_security_core_clr_check_inheritance (MonoClass *klass);
 extern void mono_security_core_clr_check_override (MonoClass *klass, MonoMethod *override, MonoMethod *base);
 
-extern void mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field);
-extern void mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method);
-extern gboolean mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, gboolean throwOnBindFailure);
+extern gboolean
+mono_security_core_clr_ensure_reflection_access_field (MonoClassField *field, MonoError *error);
+extern gboolean
+mono_security_core_clr_ensure_reflection_access_method (MonoMethod *method, MonoError *error);
+extern gboolean mono_security_core_clr_ensure_delegate_creation (MonoMethod *method, MonoError *error);
 extern MonoException* mono_security_core_clr_ensure_dynamic_method_resolved_object (gpointer ref, MonoClass *handle_class);
 
 extern gboolean mono_security_core_clr_can_access_internals (MonoImage *accessing, MonoImage* accessed);
index e3c3cbc82d57a033d5ba8ba57de299dd7468fdbc..0dfb927bc29eeae095980873a14a68a4990dc9e3 100644 (file)
@@ -5,6 +5,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright 2005-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "security-manager.h"
index 98fbbfd652169b5931dfcab650b008671f5c00f2..19ac3e8f82c496521b73ac37eb4d8cfab999adea 100644 (file)
@@ -5,6 +5,7 @@
  *     Sebastien Pouliot  <sebastien@ximian.com>
  *
  * Copyright (C) 2004-2005 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_SECURITY_MANAGER_H_
index 3f72f3f338a59069bf0323c4d7f47e035d394e4c..afd19549824a4461ac9241fda71ede99d159b97b 100644 (file)
@@ -1,5 +1,6 @@
 /*
  * Copyright 2015 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
  
 #ifndef __MONO_SEQ_POINTS_DATA_H__
index ac7dfb975998a1f290d9ab82d0923a253b8f4b58..df6a4bb8cdee7513673b29f6cd08b8ed3e3ae84b 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGENBRIDGEINTERNAL_H__
index 5e4fa165ab0efc72fd2d09482953ab52b8ee1289..74630b2c973afd4027dae0aac1c84b2515fe747f 100644 (file)
@@ -3,38 +3,10 @@
  *
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
- *
- * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
- * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
- *
- * Permission is hereby granted to use or copy this program
- * for any purpose,  provided the above notices are retained on all copies.
- * Permission to modify the code and to distribute modified code is granted,
- * provided the above notices are retained, and a notice that the code was
- * modified is included with the above copyright notice.
- *
- *
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -77,7 +49,7 @@ mono_gc_register_bridge_callbacks (MonoGCBridgeCallbacks *callbacks)
        bridge_callbacks = *callbacks;
 
        if (!bridge_processor.reset_data)
-               sgen_old_bridge_init (&bridge_processor);
+               sgen_new_bridge_init (&bridge_processor);
 }
 
 static gboolean
@@ -554,6 +526,30 @@ bridge_test_cross_reference2 (int num_sccs, MonoGCBridgeSCC **sccs, int num_xref
                sccs [i]->is_alive = TRUE;
 }
 
+/* This bridge keeps all peers with __test > 0 */
+static void
+bridge_test_positive_status (int num_sccs, MonoGCBridgeSCC **sccs, int num_xrefs, MonoGCBridgeXRef *xrefs)
+{
+       int i;
+
+       if (!mono_bridge_test_field) {
+               mono_bridge_test_field = mono_class_get_field_from_name (mono_object_get_class (sccs[0]->objs [0]), "__test");
+               g_assert (mono_bridge_test_field);
+       }
+
+       /*We mark all objects in a scc with live objects as reachable by scc*/
+       for (i = 0; i < num_sccs; ++i) {
+               int j;
+               for (j = 0; j < sccs [i]->num_objs; ++j) {
+                       if (test_scc (sccs [i], j)) {
+                               sccs [i]->is_alive = TRUE;
+                               break;
+                       }
+               }
+       }
+}
+
+
 static void
 register_test_bridge_callbacks (const char *bridge_class_name)
 {
@@ -561,9 +557,21 @@ register_test_bridge_callbacks (const char *bridge_class_name)
        callbacks.bridge_version = SGEN_BRIDGE_VERSION;
        callbacks.bridge_class_kind = bridge_test_bridge_class_kind;
        callbacks.is_bridge_object = bridge_test_is_bridge_object;
-       callbacks.cross_references = bridge_class_name[0] == '2' ? bridge_test_cross_reference2 : bridge_test_cross_reference;
+
+       switch (bridge_class_name [0]) {
+       case '2':
+               bridge_class = bridge_class_name + 1;
+               callbacks.cross_references = bridge_test_cross_reference2;
+               break;
+       case '3':
+               bridge_class = bridge_class_name + 1;
+               callbacks.cross_references = bridge_test_positive_status;
+               break;
+       default:
+               bridge_class = bridge_class_name;
+               callbacks.cross_references = bridge_test_cross_reference;
+       }
        mono_gc_register_bridge_callbacks (&callbacks);
-       bridge_class = bridge_class_name + (bridge_class_name[0] == '2' ? 1 : 0);
 }
 
 gboolean
index 28bf2caf759969be762332c9d9cc4eea504022fd..38dc44637cc05c1fea162908aec0bb741cfb0d8d 100644 (file)
@@ -1,24 +1,7 @@
 /*
  * Copyright 2011 Novell, Inc.
  * 
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index fd36c3941eeee0e0f2bc1ba44f3b1acc3b8d97b2..e9f9b1a81a7a5ddeaad89a7ae0ddac596f328fcc 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifdef SGEN_DEFINE_OBJECT_VTABLE
@@ -700,6 +689,11 @@ sgen_client_binary_protocol_evacuating_blocks (size_t block_size)
 {
 }
 
+static void G_GNUC_UNUSED
+sgen_client_binary_protocol_concurrent_sweep_end (long long timestamp)
+{
+}
+
 int sgen_thread_handshake (BOOL suspend);
 gboolean sgen_suspend_thread (SgenThreadInfo *info);
 gboolean sgen_resume_thread (SgenThreadInfo *info);
@@ -731,7 +725,7 @@ extern MonoNativeTlsKey thread_info_key;
 
 #define SGEN_TV_DECLARE(name) gint64 name
 #define SGEN_TV_GETTIME(tv) tv = mono_100ns_ticks ()
-#define SGEN_TV_ELAPSED(start,end) ((long)(end-start))
+#define SGEN_TV_ELAPSED(start,end) ((gint64)(end-start))
 
 typedef MonoSemType SgenSemaphore;
 
index 8421b903ba6f967366bba0f2d7c7b337510ac1ee..bbd97e955df2a69003dafb75b8333c0bb505859b 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -37,6 +26,7 @@
 #include "metadata/handle.h"
 #include "utils/mono-memory-model.h"
 #include "utils/mono-logger-internals.h"
+#include "sgen/sgen-thread-pool.h"
 
 #ifdef HEAVY_STATISTICS
 static guint64 stat_wbarrier_set_arrayref = 0;
@@ -1252,16 +1242,14 @@ create_allocator (int atype, gboolean slowpath)
                g_assert_not_reached ();
        }
 
-       if (atype != ATYPE_SMALL) {
-               /* size += ALLOC_ALIGN - 1; */
-               mono_mb_emit_ldloc (mb, size_var);
-               mono_mb_emit_icon (mb, SGEN_ALLOC_ALIGN - 1);
-               mono_mb_emit_byte (mb, CEE_ADD);
-               /* size &= ~(ALLOC_ALIGN - 1); */
-               mono_mb_emit_icon (mb, ~(SGEN_ALLOC_ALIGN - 1));
-               mono_mb_emit_byte (mb, CEE_AND);
-               mono_mb_emit_stloc (mb, size_var);
-       }
+       /* size += ALLOC_ALIGN - 1; */
+       mono_mb_emit_ldloc (mb, size_var);
+       mono_mb_emit_icon (mb, SGEN_ALLOC_ALIGN - 1);
+       mono_mb_emit_byte (mb, CEE_ADD);
+       /* size &= ~(ALLOC_ALIGN - 1); */
+       mono_mb_emit_icon (mb, ~(SGEN_ALLOC_ALIGN - 1));
+       mono_mb_emit_byte (mb, CEE_AND);
+       mono_mb_emit_stloc (mb, size_var);
 
        /* if (size > MAX_SMALL_OBJ_SIZE) goto slowpath */
        if (atype != ATYPE_SMALL) {
@@ -1360,14 +1348,6 @@ create_allocator (int atype, gboolean slowpath)
                mono_mb_emit_byte (mb, MONO_CEE_ADD);
                mono_mb_emit_ldarg (mb, 1);
                mono_mb_emit_byte (mb, MONO_CEE_STIND_I4);
-               /* s->chars [len] = 0; */
-               mono_mb_emit_ldloc (mb, p_var);
-               mono_mb_emit_ldloc (mb, size_var);
-               mono_mb_emit_icon (mb, 2);
-               mono_mb_emit_byte (mb, MONO_CEE_SUB);
-               mono_mb_emit_byte (mb, MONO_CEE_ADD);
-               mono_mb_emit_icon (mb, 0);
-               mono_mb_emit_byte (mb, MONO_CEE_STIND_I2);
        }
 
        /*
@@ -1591,7 +1571,7 @@ find_next_card (guint8 *card_data, guint8 *end)
 #define ARRAY_OBJ_INDEX(ptr,array,elem_size) (((char*)(ptr) - ((char*)(array) + G_STRUCT_OFFSET (MonoArray, vector))) / (elem_size))
 
 gboolean
-sgen_client_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, gboolean mod_union, ScanCopyContext ctx)
+sgen_client_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, ScanCopyContext ctx)
 {
        MonoVTable *vt = SGEN_LOAD_VTABLE (obj);
        MonoClass *klass = vt->klass;
@@ -1671,20 +1651,11 @@ LOOP_HEAD:
                                for (; elem < card_end; elem += elem_size)
                                        scan_vtype_func (obj, elem, desc, ctx.queue BINARY_PROTOCOL_ARG (elem_size));
                        } else {
-                               CopyOrMarkObjectFunc copy_func = ctx.ops->copy_or_mark_object;
+                               ScanPtrFieldFunc scan_ptr_field_func = ctx.ops->scan_ptr_field;
 
                                HEAVY_STAT (++los_array_cards);
-                               for (; elem < card_end; elem += SIZEOF_VOID_P) {
-                                       GCObject *new_;
-                                       gpointer old = *(gpointer*)elem;
-                                       if ((mod_union && old) || G_UNLIKELY (sgen_ptr_in_nursery (old))) {
-                                               HEAVY_STAT (++los_array_remsets);
-                                               copy_func ((GCObject**)elem, ctx.queue);
-                                               new_ = *(GCObject **)elem;
-                                               if (G_UNLIKELY (sgen_ptr_in_nursery (new_)))
-                                                       sgen_add_to_global_remset (elem, new_);
-                                       }
-                               }
+                               for (; elem < card_end; elem += SIZEOF_VOID_P)
+                                       scan_ptr_field_func (obj, (GCObject**)elem, ctx.queue);
                        }
 
                        binary_protocol_card_scan (first_elem, elem - first_elem);
@@ -2317,6 +2288,7 @@ void
 sgen_client_thread_register_worker (void)
 {
        mono_thread_info_register_small_id ();
+       mono_thread_info_set_name (mono_native_thread_id_get (), "SGen worker");
 }
 
 /* Variables holding start/end nursery so it won't have to be passed at every call */
@@ -2756,13 +2728,11 @@ sgen_client_log_timing (GGTimingInfo *info, mword last_major_num_sections, mword
        if (!info->is_overflow)
                sprintf (full_timing_buff, "total %.2fms, bridge %.2fms", info->stw_time / 10000.0f, (int)info->bridge_time / 10000.0f);
        if (info->generation == GENERATION_OLD)
-               mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_GC, "GC_MAJOR%s: (%s) pause %.2fms, %s major %dK/%dK los %dK/%dK",
+               mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_GC, "GC_MAJOR%s: (%s) pause %.2fms, %s los %dK/%dK",
                        info->is_overflow ? "_OVERFLOW" : "",
                        info->reason ? info->reason : "",
                        (int)info->total_time / 10000.0f,
                        full_timing_buff,
-                       major_collector->section_size * num_major_sections / 1024,
-                       major_collector->section_size * last_major_num_sections / 1024,
                        los_memory_usage / 1024,
                        last_los_memory_usage / 1024);
        else
@@ -2957,9 +2927,14 @@ sgen_client_describe_invalid_pointer (GCObject *ptr)
        sgen_bridge_describe_pointer (ptr);
 }
 
+static gboolean gc_inited;
+
 void
 mono_gc_base_init (void)
 {
+       if (gc_inited)
+               return;
+
        mono_counters_init ();
 
 #ifdef HEAVY_STATISTICS
@@ -2982,11 +2957,14 @@ mono_gc_base_init (void)
        if (mono_tls_key_get_offset (TLS_KEY_SGEN_TLAB_NEXT_ADDR) == -1)
                sgen_set_use_managed_allocator (FALSE);
 #endif
+
+       gc_inited = TRUE;
 }
 
 void
 mono_gc_base_cleanup (void)
 {
+       sgen_thread_pool_shutdown ();
 }
 
 gboolean
index 20fdb460adde86c416d941f2625f335516b3e1bb..462680a63fe5c2f59b379cf4147da2e02f8e8f15 100644 (file)
@@ -3,38 +3,10 @@
  *
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
- *
- * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
- * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
- *
- * Permission is hereby granted to use or copy this program
- * for any purpose,  provided the above notices are retained on all copies.
- * Permission to modify the code and to distribute modified code is granted,
- * provided the above notices are retained, and a notice that the code was
- * modified is included with the above copyright notice.
- *
- *
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -968,7 +940,7 @@ compare_hash_entries (const HashEntry *e1, const HashEntry *e2)
 
 DEF_QSORT_INLINE(hash_entries, HashEntry*, compare_hash_entries)
 
-static unsigned long step_1, step_2, step_3, step_4, step_5, step_6;
+static gint64 step_1, step_2, step_3, step_4, step_5, step_6;
 static int fist_pass_links, second_pass_links, sccs_links;
 static int max_sccs_links = 0;
 
index 83f991d5b867ce64bd230021fe7a96381fc09158..a93cc7734ade79befcc811e6a8a4bf05047531a8 100644 (file)
@@ -3,38 +3,9 @@
  *
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
- *
- * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
- * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
- *
- * Permission is hereby granted to use or copy this program
- * for any purpose,  provided the above notices are retained on all copies.
- * Permission to modify the code and to distribute modified code is granted,
- * provided the above notices are retained, and a notice that the code was
- * modified is included with the above copyright notice.
- *
- *
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -616,7 +587,7 @@ compare_hash_entries (const HashEntry *e1, const HashEntry *e2)
 
 DEF_QSORT_INLINE(hash_entries, HashEntry*, compare_hash_entries)
 
-static unsigned long step_1, step_2, step_3, step_4, step_5, step_6;
+static gint64 step_1, step_2, step_3, step_4, step_5, step_6;
 static int fist_pass_links, second_pass_links, sccs_links;
 static int max_sccs_links = 0;
 
index fb6fc13bc451cb9dd60a04445ac6e0a37a75f377..90c8266b341f7749da66d0ae7d3fab1a6ebbffcc 100644 (file)
@@ -5,18 +5,7 @@
  *     João Matos (joao.matos@xamarin.com)
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -78,4 +67,4 @@ mono_gc_get_restart_signal (void)
 }
 
 #endif
-#endif
\ No newline at end of file
+#endif
index 666ef3ce8cfb3103bd06720529a1a44424430e58..1c45e375af5dffb372cc6b0338189ecee7e96d82 100644 (file)
@@ -9,18 +9,7 @@
  * Copyright 2010 Novell, Inc (http://www.novell.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
 gboolean
 sgen_resume_thread (SgenThreadInfo *info)
 {
-       return thread_resume (info->client_info.info.native_handle) == KERN_SUCCESS;
+       kern_return_t ret;
+       do {
+               ret = thread_resume (info->client_info.info.native_handle);
+       } while (ret == KERN_ABORTED);
+       return ret == KERN_SUCCESS;
 }
 
 gboolean
@@ -62,11 +55,15 @@ sgen_suspend_thread (SgenThreadInfo *info)
        state = (thread_state_t) alloca (mono_mach_arch_get_thread_state_size ());
        mctx = (mcontext_t) alloca (mono_mach_arch_get_mcontext_size ());
 
-       ret = thread_suspend (info->client_info.info.native_handle);
+       do {
+               ret = thread_suspend (info->client_info.info.native_handle);
+       } while (ret == KERN_ABORTED);
        if (ret != KERN_SUCCESS)
                return FALSE;
 
-       ret = mono_mach_arch_get_thread_state (info->client_info.info.native_handle, state, &num_state);
+       do {
+               ret = mono_mach_arch_get_thread_state (info->client_info.info.native_handle, state, &num_state);
+       } while (ret == KERN_ABORTED);
        if (ret != KERN_SUCCESS)
                return FALSE;
 
@@ -128,7 +125,9 @@ sgen_thread_handshake (BOOL suspend)
                        if (!sgen_suspend_thread (info))
                                continue;
                } else {
-                       ret = thread_resume (info->client_info.info.native_handle);
+                       do {
+                               ret = thread_resume (info->client_info.info.native_handle);
+                       } while (ret == KERN_ABORTED);
                        if (ret != KERN_SUCCESS)
                                continue;
                }
index 37979a497d40939f04fe9a03de7d307f564efbb2..dc9d29ff1395ad81be62b1a63edde30f691135dc 100644 (file)
@@ -9,18 +9,7 @@
  * Copyright 2010 Novell, Inc (http://www.novell.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 15eb283ee1343486e706ebcee4f25738d122d518..4185ce07b8ad67d96965485b9516dcf02fb70a59 100644 (file)
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index e6bd1f17aa7082cdddc7f8a486aabed036c08946..764d9d72626db8df7ac104204980b8e3fb0abd45 100644 (file)
@@ -4,37 +4,11 @@
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2014 Xamarin Inc (http://www.xamarin.com)
  *
- * THIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY EXPRESSED
- * OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.
- *
- * Permission is hereby granted to use or copy this program
- * for any purpose,  provided the above notices are retained on all copies.
- * Permission to modify the code and to distribute modified code is granted,
- * provided the above notices are retained, and a notice that the code was
- * modified is included with the above copyright notice.
- *
  *
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index d9afbfa868dc9efe8a6a2eb0a31c151bb82215e2..5ca66e738af696bcbd0efcab0000a4c7bd32c9ec 100644 (file)
@@ -7,18 +7,7 @@
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index e7c4b91b7400f4e56eefd965a847c020447c9c15..917323c575af0d6f5f20122bd086e1c0c1005232 100644 (file)
@@ -7,24 +7,7 @@
  * Author:
  *  Rodrigo Kumpera (kumpera@gmail.com)
  * 
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_SGEN_TOGGLEREF_H_
index 56212ac57cf8df16137f7c781167cc76919b0561..6c3e0cf22875f07ffd8d1a3f6a77b4c61e396f3e 100644 (file)
@@ -10,6 +10,7 @@
  *
  * This file has been re-licensed under the MIT License:
  * http://opensource.org/licenses/MIT
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -846,7 +847,8 @@ create_object_from_sockaddr (struct sockaddr *saddr, int sa_size, gint32 *werror
         * the length of the entire sockaddr_in/in6, including
         * sizeof (unsigned short) of the family */
        /* We can't really avoid the +2 as all code below depends on this size - INCLUDING unix domain sockets.*/
-       data = mono_array_new_cached (domain, mono_get_byte_class (), sa_size + 2);
+       data = mono_array_new_cached (domain, mono_get_byte_class (), sa_size + 2, error);
+       return_val_if_nok (error, NULL);
 
        /* The data buffer is laid out as follows:
         * bytes 0 and 1 are the address family
@@ -1923,9 +1925,9 @@ ves_icall_System_Net_Sockets_Socket_Select_internal (MonoArray **sockets, gint32
 }
 
 static MonoObject*
-int_to_object (MonoDomain *domain, int val)
+int_to_object (MonoDomain *domain, int val, MonoError *error)
 {
-       return mono_value_box (domain, mono_get_int32_class (), &val);
+       return mono_value_box_checked (domain, mono_get_int32_class (), &val, error);
 }
 
 void
@@ -1972,7 +1974,8 @@ ves_icall_System_Net_Sockets_Socket_GetSocketOption_obj_internal (SOCKET sock, g
                return;
        }
        if (ret == -2) {
-               *obj_val = int_to_object (domain, 0);
+               *obj_val = int_to_object (domain, 0, &error);
+               mono_error_set_pending_exception (&error);
                return;
        }
 
@@ -2033,11 +2036,13 @@ ves_icall_System_Net_Sockets_Socket_GetSocketOption_obj_internal (SOCKET sock, g
                break;
        case SocketOptionName_DontLinger:
                /* construct a bool int in val - true if linger is off */
-               obj = int_to_object (domain, !linger.l_onoff);
+               obj = int_to_object (domain, !linger.l_onoff, &error);
+               mono_error_set_pending_exception (&error);
                break;
        case SocketOptionName_SendTimeout:
        case SocketOptionName_ReceiveTimeout:
-               obj = int_to_object (domain, time_ms);
+               obj = int_to_object (domain, time_ms, &error);
+               mono_error_set_pending_exception (&error);
                break;
 
 #ifdef SO_PEERCRED
@@ -2083,7 +2088,8 @@ ves_icall_System_Net_Sockets_Socket_GetSocketOption_obj_internal (SOCKET sock, g
                if (level == SocketOptionLevel_Socket && name == SocketOptionName_ExclusiveAddressUse)
                        val = val ? 0 : 1;
 #endif
-               obj = int_to_object (domain, val);
+               obj = int_to_object (domain, val, &error);
+               mono_error_set_pending_exception (&error);
        }
 
        *obj_val = obj;
@@ -2476,7 +2482,7 @@ ves_icall_System_Net_Sockets_Socket_IOControl_internal (SOCKET sock, gint32 code
 }
 
 static gboolean 
-addrinfo_to_IPHostEntry(MonoAddressInfo *info, MonoString **h_name, MonoArray **h_aliases, MonoArray **h_addr_list, gboolean add_local_ips)
+addrinfo_to_IPHostEntry (MonoAddressInfo *info, MonoString **h_name, MonoArray **h_aliases, MonoArray **h_addr_list, gboolean add_local_ips, MonoError *error)
 {
        gint32 count, i;
        MonoAddressEntry *ai = NULL;
@@ -2487,14 +2493,19 @@ addrinfo_to_IPHostEntry(MonoAddressInfo *info, MonoString **h_name, MonoArray **
        int addr_index;
        MonoDomain *domain = mono_domain_get ();
 
+       mono_error_init (error);
        addr_index = 0;
-       *h_aliases = mono_array_new (domain, mono_get_string_class (), 0);
+       *h_aliases = mono_array_new_checked (domain, mono_get_string_class (), 0, error);
+       return_val_if_nok (error, FALSE);
        if (add_local_ips) {
                local_in = (struct in_addr *) mono_get_local_interfaces (AF_INET, &nlocal_in);
                local_in6 = (struct in6_addr *) mono_get_local_interfaces (AF_INET6, &nlocal_in6);
                if (nlocal_in || nlocal_in6) {
                        char addr [INET6_ADDRSTRLEN];
-                       *h_addr_list = mono_array_new (domain, mono_get_string_class (), nlocal_in + nlocal_in6);
+                       *h_addr_list = mono_array_new_checked (domain, mono_get_string_class (), nlocal_in + nlocal_in6, error);
+                       if (!is_ok (error))
+                               goto leave;
+                       
                        if (nlocal_in) {
                                MonoString *addr_string;
                                int i;
@@ -2525,11 +2536,12 @@ addrinfo_to_IPHostEntry(MonoAddressInfo *info, MonoString **h_name, MonoArray **
                                }
                        }
 
+               leave:
                        g_free (local_in);
                        g_free (local_in6);
                        if (info)
                                mono_free_address_info (info);
-                       return TRUE;
+                       return is_ok (error);;
                }
 
                g_free (local_in);
@@ -2542,7 +2554,9 @@ addrinfo_to_IPHostEntry(MonoAddressInfo *info, MonoString **h_name, MonoArray **
                count++;
        }
 
-       *h_addr_list = mono_array_new (domain, mono_get_string_class (), count);
+       *h_addr_list = mono_array_new_checked (domain, mono_get_string_class (), count, error);
+       if (!is_ok (error))
+               goto leave2;
 
        for (ai = info->entries, i = 0; ai != NULL; ai = ai->next) {
                MonoAddress maddr;
@@ -2572,10 +2586,11 @@ addrinfo_to_IPHostEntry(MonoAddressInfo *info, MonoString **h_name, MonoArray **
                addr_index++;
        }
 
+leave2:
        if (info)
                mono_free_address_info (info);
 
-       return TRUE;
+       return is_ok (error);
 }
 
 static int
@@ -2636,8 +2651,11 @@ ves_icall_System_Net_Dns_GetHostByName_internal (MonoString *host, MonoString **
 
        g_free(hostname);
 
-       if (add_info_ok)
-               return addrinfo_to_IPHostEntry (info, h_name, h_aliases, h_addr_list, add_local_ips);
+       if (add_info_ok) {
+               MonoBoolean result = addrinfo_to_IPHostEntry (info, h_name, h_aliases, h_addr_list, add_local_ips, &error);
+               mono_error_set_pending_exception (&error);
+               return result;
+       }
        return FALSE;
 }
 
@@ -2702,7 +2720,9 @@ ves_icall_System_Net_Dns_GetHostByAddr_internal (MonoString *addr, MonoString **
        if (mono_get_address_info (hostname, 0, hint | MONO_HINT_CANONICAL_NAME | MONO_HINT_CONFIGURED_ONLY, &info) != 0)
                return FALSE;
 
-       return addrinfo_to_IPHostEntry (info, h_name, h_aliases, h_addr_list, FALSE);
+       MonoBoolean result = addrinfo_to_IPHostEntry (info, h_name, h_aliases, h_addr_list, FALSE, &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 MonoBoolean
index 1594cc52bfcdaceb0c82b6660eac85296430446a..be330aa413a76fb8e08c626c6851795937d005ce 100644 (file)
@@ -7,6 +7,7 @@
  *
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <stdlib.h>
index eadb052ccd16c46a72927fb13c0b8fe0dccda8cc..8d55a552f84dbc86d35b01deea7793039e7b007d 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2015 Xamarin, Inc (https://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 //
index bb3cf92bfd5d1906d1a53e04f4c59a0cdacc5e87..85d3234dfdb45f6c3adc7fe987a00a8387c78d10 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) Ximian, Inc. 2002
  * Copyright 2015 Xamarin, Inc (https://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __METADATA_SYSMATH_H__
index bf619214c8557f19a08553296a81a69719ee3d1c..462fa98df8143115552eeb48bc32c6e21813a529 100644 (file)
@@ -47,13 +47,6 @@ epoll_init (gint wakeup_pipe_fd)
        return TRUE;
 }
 
-static void
-epoll_cleanup (void)
-{
-       g_free (epoll_events);
-       close (epoll_fd);
-}
-
 static void
 epoll_register_fd (gint fd, gint events, gboolean is_new)
 {
@@ -127,7 +120,6 @@ epoll_event_wait (void (*callback) (gint fd, gint events, gpointer user_data), g
 
 static ThreadPoolIOBackend backend_epoll = {
        .init = epoll_init,
-       .cleanup = epoll_cleanup,
        .register_fd = epoll_register_fd,
        .remove_fd = epoll_remove_fd,
        .event_wait = epoll_event_wait,
index 093d3399dc947736f20140470c3ef08cfa306aa0..e162c3cc9be24eec2bc8dfe1558449bedb9ac314 100644 (file)
@@ -43,13 +43,6 @@ kqueue_init (gint wakeup_pipe_fd)
        return TRUE;
 }
 
-static void
-kqueue_cleanup (void)
-{
-       g_free (kqueue_events);
-       close (kqueue_fd);
-}
-
 static void
 kqueue_register_fd (gint fd, gint events, gboolean is_new)
 {
@@ -124,7 +117,6 @@ kqueue_event_wait (void (*callback) (gint fd, gint events, gpointer user_data),
 
 static ThreadPoolIOBackend backend_kqueue = {
        .init = kqueue_init,
-       .cleanup = kqueue_cleanup,
        .register_fd = kqueue_register_fd,
        .remove_fd = kqueue_remove_fd,
        .event_wait = kqueue_event_wait,
index 4adae56791b40af7ffab900966b10c267a908000..4d4cceb090269f97b4f53ecad27601c128da93a6 100644 (file)
@@ -28,12 +28,6 @@ poll_init (gint wakeup_pipe_fd)
        return TRUE;
 }
 
-static void
-poll_cleanup (void)
-{
-       g_free (poll_fds);
-}
-
 static void
 poll_register_fd (gint fd, gint events, gboolean is_new)
 {
@@ -236,7 +230,6 @@ poll_event_wait (void (*callback) (gint fd, gint events, gpointer user_data), gp
 
 static ThreadPoolIOBackend backend_poll = {
        .init = poll_init,
-       .cleanup = poll_cleanup,
        .register_fd = poll_register_fd,
        .remove_fd = poll_remove_fd,
        .event_wait = poll_event_wait,
index 11029082f8bda156b5a52d577f07c4a43e7fbbed..7aa39b2b4a5b2a435dd301663859c08e2111b3dc 100644 (file)
@@ -5,6 +5,7 @@
  *     Ludovic Henry (ludovic.henry@xamarin.com)
  *
  * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -31,7 +32,6 @@
 
 typedef struct {
        gboolean (*init) (gint wakeup_pipe_fd);
-       void     (*cleanup) (void);
        void     (*register_fd) (gint fd, gint events, gboolean is_new);
        void     (*remove_fd) (gint fd);
        gint     (*event_wait) (void (*callback) (gint fd, gint events, gpointer user_data), gpointer user_data);
@@ -245,6 +245,8 @@ filter_jobs_for_domain (gpointer key, gpointer value, gpointer user_data)
 static void
 wait_callback (gint fd, gint events, gpointer user_data)
 {
+       MonoError error;
+
        if (mono_runtime_is_shutting_down ())
                return;
 
@@ -269,13 +271,18 @@ wait_callback (gint fd, gint events, gpointer user_data)
 
                if (list && (events & EVENT_IN) != 0) {
                        MonoIOSelectorJob *job = get_job_for_event (&list, EVENT_IN);
-                       if (job)
-                               mono_threadpool_ms_enqueue_work_item (((MonoObject*) job)->vtable->domain, (MonoObject*) job);
+                       if (job) {
+                               mono_threadpool_ms_enqueue_work_item (((MonoObject*) job)->vtable->domain, (MonoObject*) job, &error);
+                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       }
+
                }
                if (list && (events & EVENT_OUT) != 0) {
                        MonoIOSelectorJob *job = get_job_for_event (&list, EVENT_OUT);
-                       if (job)
-                               mono_threadpool_ms_enqueue_work_item (((MonoObject*) job)->vtable->domain, (MonoObject*) job);
+                       if (job) {
+                               mono_threadpool_ms_enqueue_work_item (((MonoObject*) job)->vtable->domain, (MonoObject*) job, &error);
+                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       }
                }
 
                remove_fd = (events & EVENT_ERR) == EVENT_ERR;
@@ -301,6 +308,7 @@ wait_callback (gint fd, gint events, gpointer user_data)
 static void
 selector_thread (gpointer data)
 {
+       MonoError error;
        MonoGHashTable *states;
 
        io_selector_running = TRUE;
@@ -368,8 +376,10 @@ selector_thread (gpointer data)
                                                        memset (update, 0, sizeof (ThreadPoolIOUpdate));
                                        }
 
-                                       for (; list; list = mono_mlist_remove_item (list, list))
-                                               mono_threadpool_ms_enqueue_work_item (mono_object_domain (mono_mlist_get_data (list)), mono_mlist_get_data (list));
+                                       for (; list; list = mono_mlist_remove_item (list, list)) {
+                                               mono_threadpool_ms_enqueue_work_item (mono_object_domain (mono_mlist_get_data (list)), mono_mlist_get_data (list), &error);
+                                               mono_error_raise_exception (&error); /* FIXME don't raise here */
+                                       }
 
                                        mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_THREADPOOL, "io threadpool: del fd %3d", fd);
                                        threadpool_io->backend.remove_fd (fd);
@@ -526,8 +536,9 @@ initialize (void)
        if (!threadpool_io->backend.init (threadpool_io->wakeup_pipes [0]))
                g_error ("initialize: backend->init () failed");
 
-       if (!mono_thread_create_internal (mono_get_root_domain (), selector_thread, NULL, TRUE, SMALL_STACK))
-               g_error ("initialize: mono_thread_create_internal () failed");
+       MonoError error;
+       if (!mono_thread_create_internal (mono_get_root_domain (), selector_thread, NULL, TRUE, SMALL_STACK, &error))
+               g_error ("initialize: mono_thread_create_internal () failed due to %s", mono_error_get_message (&error));
 }
 
 static void
@@ -540,24 +551,6 @@ cleanup (void)
        selector_thread_wakeup ();
        while (io_selector_running)
                mono_thread_info_usleep (1000);
-
-       mono_coop_mutex_destroy (&threadpool_io->updates_lock);
-       mono_coop_cond_destroy (&threadpool_io->updates_cond);
-
-       threadpool_io->backend.cleanup ();
-
-#if !defined(HOST_WIN32)
-       close (threadpool_io->wakeup_pipes [0]);
-       close (threadpool_io->wakeup_pipes [1]);
-#else
-       closesocket (threadpool_io->wakeup_pipes [0]);
-       closesocket (threadpool_io->wakeup_pipes [1]);
-#endif
-
-       g_assert (threadpool_io);
-       g_free (threadpool_io);
-       threadpool_io = NULL;
-       g_assert (!threadpool_io);
 }
 
 void
@@ -573,7 +566,7 @@ ves_icall_System_IOSelector_Add (gpointer handle, MonoIOSelectorJob *job)
 
        g_assert (handle >= 0);
 
-       g_assert (job->operation == EVENT_IN ^ job->operation == EVENT_OUT);
+       g_assert ((job->operation == EVENT_IN) ^ (job->operation == EVENT_OUT));
        g_assert (job->callback);
 
        if (mono_runtime_is_shutting_down ())
index ba3d3efd39370d493c5671c8f1a818677164b9ef..69ade32e593ef5fc5db50665d5924f1069595dcb 100644 (file)
@@ -5,6 +5,7 @@
  *     Ludovic Henry (ludovic.henry@xamarin.com)
  *
  * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 //
@@ -344,16 +345,16 @@ cleanup (void)
        mono_coop_mutex_unlock (&threadpool->active_threads_lock);
 }
 
-void
-mono_threadpool_ms_enqueue_work_item (MonoDomain *domain, MonoObject *work_item)
+gboolean
+mono_threadpool_ms_enqueue_work_item (MonoDomain *domain, MonoObject *work_item, MonoError *error)
 {
        static MonoClass *threadpool_class = NULL;
        static MonoMethod *unsafe_queue_custom_work_item_method = NULL;
-       MonoError error;
        MonoDomain *current_domain;
        MonoBoolean f;
        gpointer args [2];
 
+       mono_error_init (error);
        g_assert (work_item);
 
        if (!threadpool_class)
@@ -370,17 +371,21 @@ mono_threadpool_ms_enqueue_work_item (MonoDomain *domain, MonoObject *work_item)
 
        current_domain = mono_domain_get ();
        if (current_domain == domain) {
-               mono_runtime_invoke_checked (unsafe_queue_custom_work_item_method, NULL, args, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               mono_runtime_invoke_checked (unsafe_queue_custom_work_item_method, NULL, args, error);
+               return_val_if_nok (error, FALSE);
        } else {
                mono_thread_push_appdomain_ref (domain);
                if (mono_domain_set (domain, FALSE)) {
-                       mono_runtime_invoke_checked (unsafe_queue_custom_work_item_method, NULL, args, &error);
-                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       mono_runtime_invoke_checked (unsafe_queue_custom_work_item_method, NULL, args, error);
+                       if (!is_ok (error)) {
+                               mono_thread_pop_appdomain_ref ();
+                               return FALSE;
+                       }
                        mono_domain_set (current_domain, TRUE);
                }
                mono_thread_pop_appdomain_ref ();
        }
+       return TRUE;
 }
 
 /* LOCKING: threadpool->domains_lock must be held */
@@ -524,7 +529,7 @@ worker_park (void)
                if (interrupted)
                        goto done;
 
-               if (mono_coop_cond_timedwait (&threadpool->parked_threads_cond, &threadpool->active_threads_lock, rand_next ((void **)rand_handle, 5 * 1000, 60 * 1000)) != 0)
+               if (mono_coop_cond_timedwait (&threadpool->parked_threads_cond, &threadpool->active_threads_lock, rand_next (&rand_handle, 5 * 1000, 60 * 1000)) != 0)
                        timeout = TRUE;
 
                mono_thread_info_uninstall_interrupt (&interrupted);
@@ -587,7 +592,8 @@ worker_thread (gpointer data)
        thread = mono_thread_internal_current ();
        g_assert (thread);
 
-       mono_thread_set_name_internal (thread, mono_string_new (mono_domain_get (), "Threadpool worker"), FALSE);
+       mono_thread_set_name_internal (thread, mono_string_new (mono_get_root_domain (), "Threadpool worker"), FALSE, &error);
+       mono_error_assert_ok (&error);
 
        mono_coop_mutex_lock (&threadpool->active_threads_lock);
        g_ptr_array_add (threadpool->working_threads, thread);
@@ -736,7 +742,8 @@ worker_try_create (void)
                counter._.active ++;
        });
 
-       if ((thread = mono_thread_create_internal (mono_get_root_domain (), worker_thread, NULL, TRUE, 0)) != NULL) {
+       MonoError error;
+       if ((thread = mono_thread_create_internal (mono_get_root_domain (), worker_thread, NULL, TRUE, 0, &error)) != NULL) {
                threadpool->worker_creation_current_count += 1;
 
                mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_THREADPOOL, "[%p] try create worker, created %p, now = %d count = %d", mono_native_thread_id_get (), thread->tid, now, threadpool->worker_creation_current_count);
@@ -744,7 +751,8 @@ worker_try_create (void)
                return TRUE;
        }
 
-       mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_THREADPOOL, "[%p] try create worker, failed: could not create thread", mono_native_thread_id_get ());
+       mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_THREADPOOL, "[%p] try create worker, failed: could not create thread due to %s", mono_native_thread_id_get (), mono_error_get_message (&error));
+       mono_error_cleanup (&error);
 
        COUNTER_ATOMIC (counter, {
                counter._.working --;
@@ -959,6 +967,7 @@ monitor_thread (void)
 static void
 monitor_ensure_running (void)
 {
+       MonoError error;
        for (;;) {
                switch (monitor_status) {
                case MONITOR_STATUS_REQUESTED:
@@ -970,8 +979,10 @@ monitor_ensure_running (void)
                        if (mono_runtime_is_shutting_down ())
                                return;
                        if (InterlockedCompareExchange (&monitor_status, MONITOR_STATUS_REQUESTED, MONITOR_STATUS_NOT_RUNNING) == MONITOR_STATUS_NOT_RUNNING) {
-                               if (!mono_thread_create_internal (mono_get_root_domain (), monitor_thread, NULL, TRUE, SMALL_STACK))
+                               if (!mono_thread_create_internal (mono_get_root_domain (), monitor_thread, NULL, TRUE, SMALL_STACK, &error)) {
                                        monitor_status = MONITOR_STATUS_NOT_RUNNING;
+                                       mono_error_cleanup (&error);
+                               }
                                return;
                        }
                        break;
@@ -1314,10 +1325,9 @@ mono_threadpool_ms_cleanup (void)
 }
 
 MonoAsyncResult *
-mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMethod *method, gpointer *params)
+mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMethod *method, gpointer *params, MonoError *error)
 {
        static MonoClass *async_call_klass = NULL;
-       MonoError error;
        MonoMethodMessage *message;
        MonoAsyncResult *async_result;
        MonoAsyncCall *async_call;
@@ -1329,10 +1339,12 @@ mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMet
 
        mono_lazy_initialize (&status, initialize);
 
+       mono_error_init (error);
+
        message = mono_method_call_message_new (method, params, mono_get_delegate_invoke (method->klass), (params != NULL) ? (&async_callback) : NULL, (params != NULL) ? (&state) : NULL);
 
-       async_call = (MonoAsyncCall*) mono_object_new_checked (domain, async_call_klass, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       async_call = (MonoAsyncCall*) mono_object_new_checked (domain, async_call_klass, error);
+       return_val_if_nok (error, NULL);
 
        MONO_OBJECT_SETREF (async_call, msg, message);
        MONO_OBJECT_SETREF (async_call, state, state);
@@ -1345,7 +1357,8 @@ mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMet
        async_result = mono_async_result_new (domain, NULL, async_call->state, NULL, (MonoObject*) async_call);
        MONO_OBJECT_SETREF (async_result, async_delegate, target);
 
-       mono_threadpool_ms_enqueue_work_item (domain, (MonoObject*) async_result);
+       mono_threadpool_ms_enqueue_work_item (domain, (MonoObject*) async_result, error);
+       return_val_if_nok (error, NULL);
 
        return async_result;
 }
@@ -1353,6 +1366,7 @@ mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMet
 MonoObject *
 mono_threadpool_ms_end_invoke (MonoAsyncResult *ares, MonoArray **out_args, MonoObject **exc)
 {
+       MonoError error;
        MonoAsyncCall *ac;
 
        g_assert (exc);
@@ -1382,7 +1396,9 @@ mono_threadpool_ms_end_invoke (MonoAsyncResult *ares, MonoArray **out_args, Mono
                } else {
                        wait_event = CreateEvent (NULL, TRUE, FALSE, NULL);
                        g_assert(wait_event);
-                       MONO_OBJECT_SETREF (ares, handle, (MonoObject*) mono_wait_handle_new (mono_object_domain (ares), wait_event));
+                       MonoWaitHandle *wait_handle = mono_wait_handle_new (mono_object_domain (ares), wait_event, &error);
+                       mono_error_raise_exception (&error); /* FIXME don't raise here */
+                       MONO_OBJECT_SETREF (ares, handle, (MonoObject*) wait_handle);
                }
                mono_monitor_exit ((MonoObject*) ares);
                MONO_PREPARE_BLOCKING;
@@ -1585,7 +1601,9 @@ void
 ves_icall_System_Threading_ThreadPool_ReportThreadStatus (MonoBoolean is_working)
 {
        // TODO
-       mono_raise_exception (mono_get_exception_not_implemented (NULL));
+       MonoError error;
+       mono_error_set_not_implemented (&error, "");
+       mono_error_set_pending_exception (&error);
 }
 
 MonoBoolean
@@ -1598,7 +1616,9 @@ MonoBoolean G_GNUC_UNUSED
 ves_icall_System_Threading_ThreadPool_PostQueuedCompletionStatus (MonoNativeOverlapped *native_overlapped)
 {
        /* This copy the behavior of the current Mono implementation */
-       mono_raise_exception (mono_get_exception_not_implemented (NULL));
+       MonoError error;
+       mono_error_set_not_implemented (&error, "");
+       mono_error_set_pending_exception (&error);
        return FALSE;
 }
 
index 8aee68c4c035c10b0cfb88870a771de5ccc79d4e..9812ee57ba2a989617ac1b96f54997a3cc3c0b58 100644 (file)
@@ -15,7 +15,7 @@ void
 mono_threadpool_ms_cleanup (void);
 
 MonoAsyncResult *
-mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMethod *method, gpointer *params);
+mono_threadpool_ms_begin_invoke (MonoDomain *domain, MonoObject *target, MonoMethod *method, gpointer *params, MonoError *error);
 MonoObject *
 mono_threadpool_ms_end_invoke (MonoAsyncResult *ares, MonoArray **out_args, MonoObject **exc);
 
@@ -59,7 +59,7 @@ ves_icall_System_Threading_ThreadPool_IsThreadPoolHosted (void);
 
 /* Internals */
 
-void
-mono_threadpool_ms_enqueue_work_item (MonoDomain *domain, MonoObject *work_item);
+gboolean
+mono_threadpool_ms_enqueue_work_item (MonoDomain *domain, MonoObject *work_item, MonoError *error);
 
 #endif // _MONO_THREADPOOL_MICROSOFT_H_
index b097a377fe6a957221c7fe24a493ba2717b65e87..23a7eefcd771587febe75cf6b7903b401b4aac23 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2001 Ximian, Inc
  * (C) Copyright 2002-2006 Novell, Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _MONO_METADATA_THREADS_TYPES_H_
@@ -64,7 +65,7 @@ typedef void (*MonoThreadCleanupFunc) (MonoNativeThreadId tid);
 /* INFO has type MonoThreadInfo* */
 typedef void (*MonoThreadNotifyPendingExcFunc) (gpointer info);
 
-MonoInternalThread* mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gboolean threadpool_thread, guint32 stack_size);
+MonoInternalThread* mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gboolean threadpool_thread, guint32 stack_size, MonoError *error);
 
 void mono_threads_install_cleanup (MonoThreadCleanupFunc func);
 
@@ -95,10 +96,10 @@ gboolean ves_icall_System_Threading_Events_ResetEvent_internal (HANDLE handle);
 void ves_icall_System_Threading_Events_CloseEvent_internal (HANDLE handle);
 HANDLE ves_icall_System_Threading_Events_OpenEvent_internal (MonoString *name, gint32 rights, gint32 *error);
 
-gint32 ves_icall_System_Threading_WaitHandle_WaitAll_internal(MonoArray *mono_handles, gint32 ms, gboolean exitContext);
-gint32 ves_icall_System_Threading_WaitHandle_WaitAny_internal(MonoArray *mono_handles, gint32 ms, gboolean exitContext);
-gint32 ves_icall_System_Threading_WaitHandle_WaitOne_internal(HANDLE handle, gint32 ms, gboolean exitContext);
-gint32 ves_icall_System_Threading_WaitHandle_SignalAndWait_Internal (HANDLE toSignal, HANDLE toWait, gint32 ms, gboolean exitContext);
+gint32 ves_icall_System_Threading_WaitHandle_WaitAll_internal(MonoArray *mono_handles, gint32 ms);
+gint32 ves_icall_System_Threading_WaitHandle_WaitAny_internal(MonoArray *mono_handles, gint32 ms);
+gint32 ves_icall_System_Threading_WaitHandle_WaitOne_internal(HANDLE handle, gint32 ms);
+gint32 ves_icall_System_Threading_WaitHandle_SignalAndWait_Internal (HANDLE toSignal, HANDLE toWait, gint32 ms);
 
 MonoArray* ves_icall_System_Threading_Thread_ByteArrayToRootDomain (MonoArray *arr);
 MonoArray* ves_icall_System_Threading_Thread_ByteArrayToCurrentDomain (MonoArray *arr);
@@ -217,7 +218,7 @@ MONO_API MonoException* mono_thread_get_undeniable_exception (void);
 
 MonoException* mono_thread_get_and_clear_pending_exception (void);
 
-void mono_thread_set_name_internal (MonoInternalThread *this_obj, MonoString *name, gboolean managed);
+void mono_thread_set_name_internal (MonoInternalThread *this_obj, MonoString *name, gboolean managed, MonoError *error);
 
 void mono_runtime_set_has_tls_get (gboolean val);
 gboolean mono_runtime_has_tls_get (void);
@@ -244,6 +245,9 @@ gpointer mono_get_special_static_data_for_thread (MonoInternalThread *thread, gu
 MonoException* mono_thread_resume_interruption (void);
 void mono_threads_perform_thread_dump (void);
 
+gboolean
+mono_thread_create_checked (MonoDomain *domain, gpointer func, gpointer arg, MonoError *error);
+
 MonoThread *
 mono_thread_attach_full (MonoDomain *domain, gboolean force_attach, MonoError *error);
 
index d53f160758820a990d96a8906650537544365912..34f3be0d4887eb48835f6381a8e12e1598e16a6f 100644 (file)
@@ -9,6 +9,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -453,7 +454,9 @@ static void thread_cleanup (MonoInternalThread *thread)
        }
        mono_release_type_locks (thread);
 
-       mono_profiler_thread_end (thread->tid);
+       /* Can happen when we attach the profiler helper thread in order to heapshot. */
+       if (!mono_thread_info_lookup (MONO_UINT_TO_NATIVE_THREAD_ID (thread->tid))->tools_thread)
+               mono_profiler_thread_end (thread->tid);
 
        if (thread == mono_thread_internal_current ()) {
                /*
@@ -615,23 +618,25 @@ create_internal_thread (MonoError *error)
        return thread;
 }
 
-static void
-init_root_domain_thread (MonoInternalThread *thread, MonoThread *candidate)
+static gboolean
+init_root_domain_thread (MonoInternalThread *thread, MonoThread *candidate, MonoError *error)
 {
-       MonoError error;
        MonoDomain *domain = mono_get_root_domain ();
 
+       mono_error_init (error);
        if (!candidate || candidate->obj.vtable->domain != domain) {
-               candidate = new_thread_with_internal (domain, thread, &error);
-               mono_error_raise_exception (&error); /* FIXME don't raise here */
+               candidate = new_thread_with_internal (domain, thread, error);
+               return_val_if_nok (error, FALSE);
        }
        set_current_thread_for_domain (domain, thread, candidate);
        g_assert (!thread->root_domain_thread);
        MONO_OBJECT_SETREF (thread, root_domain_thread, candidate);
+       return TRUE;
 }
 
 static guint32 WINAPI start_wrapper_internal(void *data)
 {
+       MonoError error;
        MonoThreadInfo *info;
        StartInfo *start_info = (StartInfo *)data;
        guint32 (*start_func)(void *);
@@ -680,7 +685,8 @@ static guint32 WINAPI start_wrapper_internal(void *data)
        /* We have to do this here because mono_thread_new_init()
           requires that root_domain_thread is set up. */
        thread_adjust_static_data (internal);
-       init_root_domain_thread (internal, start_info->obj);
+       init_root_domain_thread (internal, start_info->obj, &error);
+       mono_error_raise_exception (&error); /* FIXME don't raise here */
 
        /* This MUST be called before any managed code can be
         * executed, as it calls the callback function that (for the
@@ -724,6 +730,7 @@ static guint32 WINAPI start_wrapper_internal(void *data)
        if (internal->name && (internal->flags & MONO_THREAD_FLAG_NAME_SET)) {
                char *tname = g_utf16_to_utf8 (internal->name, internal->name_len, NULL, NULL, NULL);
                mono_profiler_thread_name (internal->tid, tname);
+               mono_thread_info_set_name (MONO_UINT_TO_NATIVE_THREAD_ID (internal->tid), tname);
                g_free (tname);
        }
        /* start_func is set only for unmanaged start functions */
@@ -786,7 +793,7 @@ static guint32 WINAPI start_wrapper(void *data)
  */
 static gboolean
 create_thread (MonoThread *thread, MonoInternalThread *internal, StartInfo *start_info, gboolean threadpool_thread, guint32 stack_size,
-                          gboolean throw_on_failure)
+                          MonoError *error)
 {
        HANDLE thread_handle;
        MonoNativeThreadId tid;
@@ -798,6 +805,8 @@ create_thread (MonoThread *thread, MonoInternalThread *internal, StartInfo *star
         */
        mono_threads_join_threads ();
 
+       mono_error_init (error);
+
        mono_threads_lock ();
        if (shutting_down) {
                g_free (start_info);
@@ -833,15 +842,12 @@ create_thread (MonoThread *thread, MonoInternalThread *internal, StartInfo *star
                                                                                                stack_size, create_flags, &tid);
 
        if (thread_handle == NULL) {
-               /* The thread couldn't be created, so throw an exception */
+               /* The thread couldn't be created, so set an exception */
                mono_threads_lock ();
                mono_g_hash_table_remove (threads_starting_up, thread);
                mono_threads_unlock ();
                g_free (start_info);
-               if (throw_on_failure)
-                       mono_raise_exception (mono_get_exception_execution_engine ("Couldn't create thread"));
-               else
-                       g_warning ("%s: CreateThread error 0x%x", __func__, GetLastError ());
+               mono_error_set_execution_engine (error, "Couldn't create thread. Error 0x%x", GetLastError());
                return FALSE;
        }
        THREAD_DEBUG (g_message ("%s: Started thread ID %"G_GSIZE_FORMAT" (handle %p)", __func__, tid, thread_handle));
@@ -909,19 +915,20 @@ guint32 mono_threads_get_default_stacksize (void)
  *   ARG should not be a GC reference.
  */
 MonoInternalThread*
-mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gboolean threadpool_thread, guint32 stack_size)
+mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gboolean threadpool_thread, guint32 stack_size, MonoError *error)
 {
-       MonoError error;
        MonoThread *thread;
        MonoInternalThread *internal;
        StartInfo *start_info;
        gboolean res;
 
-       thread = create_thread_object (domain, &error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       mono_error_init (error);
 
-       internal = create_internal_thread (&error);
-       mono_error_raise_exception (&error); /* FIXME don't raise here */
+       thread = create_thread_object (domain, error);
+       return_val_if_nok (error, NULL);
+
+       internal = create_internal_thread (error);
+       return_val_if_nok (error, NULL);
 
        MONO_OBJECT_SETREF (thread, internal_thread, internal);
 
@@ -930,9 +937,8 @@ mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gb
        start_info->obj = thread;
        start_info->start_arg = arg;
 
-       res = create_thread (thread, internal, start_info, threadpool_thread, stack_size, TRUE);
-       if (!res)
-               return NULL;
+       res = create_thread (thread, internal, start_info, threadpool_thread, stack_size, error);
+       return_val_if_nok (error, NULL);
 
        /* Check that the managed and unmanaged layout of MonoInternalThread matches */
 #ifndef MONO_CROSS_COMPILE
@@ -946,7 +952,15 @@ mono_thread_create_internal (MonoDomain *domain, gpointer func, gpointer arg, gb
 void
 mono_thread_create (MonoDomain *domain, gpointer func, gpointer arg)
 {
-       mono_thread_create_internal (domain, func, arg, FALSE, 0);
+       MonoError error;
+       if (!mono_thread_create_checked (domain, func, arg, &error))
+               mono_error_cleanup (&error);
+}
+
+gboolean
+mono_thread_create_checked (MonoDomain *domain, gpointer func, gpointer arg, MonoError *error)
+{
+       return (NULL != mono_thread_create_internal (domain, func, arg, FALSE, 0, error));
 }
 
 MonoThread *
@@ -1018,7 +1032,9 @@ mono_thread_attach_full (MonoDomain *domain, gboolean force_attach, MonoError *e
 
        thread_adjust_static_data (thread);
 
-       init_root_domain_thread (thread, current_thread);
+       init_root_domain_thread (thread, current_thread, error);
+       return_val_if_nok (error, NULL);
+
        if (domain != mono_get_root_domain ())
                set_current_thread_for_domain (domain, thread, current_thread);
 
@@ -1035,8 +1051,10 @@ mono_thread_attach_full (MonoDomain *domain, gboolean force_attach, MonoError *e
                        mono_thread_attach_cb (MONO_NATIVE_THREAD_ID_TO_UINT (tid), staddr + stsize);
        }
 
-       // FIXME: Need a separate callback
-       mono_profiler_thread_start (MONO_NATIVE_THREAD_ID_TO_UINT (tid));
+       /* Can happen when we attach the profiler helper thread in order to heapshot. */
+       if (!info->tools_thread)
+               // FIXME: Need a separate callback
+               mono_profiler_thread_start (MONO_NATIVE_THREAD_ID_TO_UINT (tid));
 
        return current_thread;
 }
@@ -1122,6 +1140,7 @@ HANDLE
 ves_icall_System_Threading_Thread_Thread_internal (MonoThread *this_obj,
                                                                                                   MonoObject *start)
 {
+       MonoError error;
        StartInfo *start_info;
        MonoInternalThread *internal;
        gboolean res;
@@ -1152,8 +1171,9 @@ ves_icall_System_Threading_Thread_Thread_internal (MonoThread *this_obj,
        start_info->obj = this_obj;
        g_assert (this_obj->obj.vtable->domain == mono_domain_get ());
 
-       res = create_thread (this_obj, internal, start_info, FALSE, 0, FALSE);
+       res = create_thread (this_obj, internal, start_info, FALSE, 0, &error);
        if (!res) {
+               mono_error_cleanup (&error);
                UNLOCK_THREAD (internal);
                return NULL;
        }
@@ -1344,14 +1364,16 @@ ves_icall_System_Threading_Thread_GetName_internal (MonoInternalThread *this_obj
 }
 
 void 
-mono_thread_set_name_internal (MonoInternalThread *this_obj, MonoString *name, gboolean managed)
+mono_thread_set_name_internal (MonoInternalThread *this_obj, MonoString *name, gboolean managed, MonoError *error)
 {
        LOCK_THREAD (this_obj);
 
+       mono_error_init (error);
+
        if ((this_obj->flags & MONO_THREAD_FLAG_NAME_SET) && !this_obj->threadpool_thread) {
                UNLOCK_THREAD (this_obj);
                
-               mono_raise_exception (mono_get_exception_invalid_operation ("Thread.Name can only be set once."));
+               mono_error_set_invalid_operation (error, "Thread.Name can only be set once.");
                return;
        }
        if (this_obj->name) {
@@ -1382,7 +1404,9 @@ mono_thread_set_name_internal (MonoInternalThread *this_obj, MonoString *name, g
 void 
 ves_icall_System_Threading_Thread_SetName_internal (MonoInternalThread *this_obj, MonoString *name)
 {
-       mono_thread_set_name_internal (this_obj, name, TRUE);
+       MonoError error;
+       mono_thread_set_name_internal (this_obj, name, TRUE, &error);
+       mono_error_set_pending_exception (&error);
 }
 
 /*
@@ -1424,17 +1448,18 @@ ves_icall_System_Threading_Thread_SetPriority (MonoThread *this_obj, int priorit
 /* If the array is already in the requested domain, we just return it,
    otherwise we return a copy in that domain. */
 static MonoArray*
-byte_array_to_domain (MonoArray *arr, MonoDomain *domain)
+byte_array_to_domain (MonoArray *arr, MonoDomain *domain, MonoError *error)
 {
        MonoArray *copy;
 
+       mono_error_init (error);
        if (!arr)
                return NULL;
 
        if (mono_object_domain (arr) == domain)
                return arr;
 
-       copy = mono_array_new (domain, mono_defaults.byte_class, arr->max_length);
+       copy = mono_array_new_checked (domain, mono_defaults.byte_class, arr->max_length, error);
        memmove (mono_array_addr (copy, guint8, 0), mono_array_addr (arr, guint8, 0), arr->max_length);
        return copy;
 }
@@ -1442,13 +1467,19 @@ byte_array_to_domain (MonoArray *arr, MonoDomain *domain)
 MonoArray*
 ves_icall_System_Threading_Thread_ByteArrayToRootDomain (MonoArray *arr)
 {
-       return byte_array_to_domain (arr, mono_get_root_domain ());
+       MonoError error;
+       MonoArray *result = byte_array_to_domain (arr, mono_get_root_domain (), &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 MonoArray*
 ves_icall_System_Threading_Thread_ByteArrayToCurrentDomain (MonoArray *arr)
 {
-       return byte_array_to_domain (arr, mono_domain_get ());
+       MonoError error;
+       MonoArray *result = byte_array_to_domain (arr, mono_domain_get (), &error);
+       mono_error_set_pending_exception (&error);
+       return result;
 }
 
 MonoThread *
@@ -1582,8 +1613,7 @@ mono_wait_uninterrupted (MonoInternalThread *thread, gboolean multiple, guint32
        return ret;
 }
 
-/* FIXME: exitContext isnt documented */
-gint32 ves_icall_System_Threading_WaitHandle_WaitAll_internal(MonoArray *mono_handles, gint32 ms, gboolean exitContext)
+gint32 ves_icall_System_Threading_WaitHandle_WaitAll_internal(MonoArray *mono_handles, gint32 ms)
 {
        HANDLE *handles;
        guint32 numhandles;
@@ -1616,11 +1646,11 @@ gint32 ves_icall_System_Threading_WaitHandle_WaitAll_internal(MonoArray *mono_ha
 
        g_free(handles);
 
-       return ret;
+       /* WAIT_FAILED in waithandle.cs is different from WAIT_FAILED in Win32 API */
+       return ret == WAIT_FAILED ? 0x7fffffff : ret;
 }
 
-/* FIXME: exitContext isnt documented */
-gint32 ves_icall_System_Threading_WaitHandle_WaitAny_internal(MonoArray *mono_handles, gint32 ms, gboolean exitContext)
+gint32 ves_icall_System_Threading_WaitHandle_WaitAny_internal(MonoArray *mono_handles, gint32 ms)
 {
        HANDLE handles [MAXIMUM_WAIT_OBJECTS];
        uintptr_t numhandles;
@@ -1663,12 +1693,12 @@ gint32 ves_icall_System_Threading_WaitHandle_WaitAny_internal(MonoArray *mono_ha
                return ret - WAIT_ABANDONED_0;
        }
        else {
-               return ret;
+               /* WAIT_FAILED in waithandle.cs is different from WAIT_FAILED in Win32 API */
+               return ret == WAIT_FAILED ? 0x7fffffff : ret;
        }
 }
 
-/* FIXME: exitContext isnt documented */
-gint32 ves_icall_System_Threading_WaitHandle_WaitOne_internal(HANDLE handle, gint32 ms, gboolean exitContext)
+gint32 ves_icall_System_Threading_WaitHandle_WaitOne_internal(HANDLE handle, gint32 ms)
 {
        guint32 ret;
        MonoInternalThread *thread = mono_thread_internal_current ();
@@ -1687,11 +1717,12 @@ gint32 ves_icall_System_Threading_WaitHandle_WaitOne_internal(HANDLE handle, gin
        
        mono_thread_clr_state (thread, ThreadState_WaitSleepJoin);
        
-       return ret;
+       /* WAIT_FAILED in waithandle.cs is different from WAIT_FAILED in Win32 API */
+       return ret == WAIT_FAILED ? 0x7fffffff : ret;
 }
 
 gint32
-ves_icall_System_Threading_WaitHandle_SignalAndWait_Internal (HANDLE toSignal, HANDLE toWait, gint32 ms, gboolean exitContext)
+ves_icall_System_Threading_WaitHandle_SignalAndWait_Internal (HANDLE toSignal, HANDLE toWait, gint32 ms)
 {
        guint32 ret;
        MonoInternalThread *thread = mono_thread_internal_current ();
@@ -1709,7 +1740,8 @@ ves_icall_System_Threading_WaitHandle_SignalAndWait_Internal (HANDLE toSignal, H
        
        mono_thread_clr_state (thread, ThreadState_WaitSleepJoin);
 
-       return ret;
+       /* WAIT_FAILED in waithandle.cs is different from WAIT_FAILED in Win32 API */
+       return ret == WAIT_FAILED ? 0x7fffffff : ret;
 }
 
 HANDLE ves_icall_System_Threading_Mutex_CreateMutex_internal (MonoBoolean owned, MonoString *name, MonoBoolean *created)
@@ -2252,8 +2284,9 @@ mono_thread_internal_reset_abort (MonoInternalThread *thread)
 MonoObject*
 ves_icall_System_Threading_Thread_GetAbortExceptionState (MonoThread *this_obj)
 {
+       MonoError error;
        MonoInternalThread *thread = this_obj->internal_thread;
-       MonoObject *state, *deserialized = NULL, *exc;
+       MonoObject *state, *deserialized = NULL;
        MonoDomain *domain;
 
        if (!thread->abort_state_handle)
@@ -2266,12 +2299,14 @@ ves_icall_System_Threading_Thread_GetAbortExceptionState (MonoThread *this_obj)
        if (mono_object_domain (state) == domain)
                return state;
 
-       deserialized = mono_object_xdomain_representation (state, domain, &exc);
+       deserialized = mono_object_xdomain_representation (state, domain, &error);
 
        if (!deserialized) {
                MonoException *invalid_op_exc = mono_get_exception_invalid_operation ("Thread.ExceptionState cannot access an ExceptionState from a different AppDomain");
-               if (exc)
+               if (!is_ok (&error)) {
+                       MonoObject *exc = (MonoObject*)mono_error_convert_to_exception (&error);
                        MONO_OBJECT_SETREF (invalid_op_exc, inner_ex, exc);
+               }
                mono_set_pending_exception (invalid_op_exc);
                return NULL;
        }
@@ -3508,8 +3543,12 @@ mono_threads_get_thread_dump (MonoArray **out_threads, MonoArray **out_stack_fra
        ud.frames = g_new0 (MonoStackFrameInfo, 256);
        ud.max_frames = 256;
 
-       *out_threads = mono_array_new (domain, mono_defaults.thread_class, nthreads);
-       *out_stack_frames = mono_array_new (domain, mono_defaults.array_class, nthreads);
+       *out_threads = mono_array_new_checked (domain, mono_defaults.thread_class, nthreads, &error);
+       if (!is_ok (&error))
+               goto leave;
+       *out_stack_frames = mono_array_new_checked (domain, mono_defaults.array_class, nthreads, &error);
+       if (!is_ok (&error))
+               goto leave;
 
        for (tindex = 0; tindex < nthreads; ++tindex) {
                MonoInternalThread *thread = thread_array [tindex];
@@ -3528,7 +3567,9 @@ mono_threads_get_thread_dump (MonoArray **out_threads, MonoArray **out_stack_fra
 
                mono_array_setref_fast (*out_threads, tindex, mono_thread_current_for_thread (thread));
 
-               thread_frames = mono_array_new (domain, mono_defaults.stack_frame_class, ud.nframes);
+               thread_frames = mono_array_new_checked (domain, mono_defaults.stack_frame_class, ud.nframes, &error);
+               if (!is_ok (&error))
+                       goto leave;
                mono_array_setref_fast (*out_stack_frames, tindex, thread_frames);
 
                for (i = 0; i < ud.nframes; ++i) {
index 99762e9da005e13e94897fe763dfe67f00c83341..5a0c79c7cca732b1ffeff80292a6ad943d1114e5 100644 (file)
@@ -34,7 +34,10 @@ extern MONO_API void mono_thread_stop (MonoThread *thread);
 
 extern MONO_API void mono_thread_new_init (intptr_t tid, void* stack_start,
                                  void* func);
-extern MONO_API void mono_thread_create (MonoDomain *domain, void* func, void* arg);
+
+extern MONO_RT_EXTERNAL_ONLY MONO_API void
+mono_thread_create (MonoDomain *domain, void* func, void* arg);
+
 extern MONO_API MonoThread *mono_thread_attach (MonoDomain *domain);
 extern MONO_API void mono_thread_detach (MonoThread *thread);
 extern MONO_API void mono_thread_exit (void);
index e52f90aca0c155d453e40a77a1fdb3db805708ed..c3da0227e3c78f729968ffa1e9c4391a47a84e51 100644 (file)
@@ -7,6 +7,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Rodrigo Kumpera
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 
@@ -884,12 +885,11 @@ mono_type_is_valid_in_context (VerifyContext *ctx, MonoType *type)
 
        klass = mono_class_from_mono_type (type);
        mono_class_init (klass);
-       if (mono_loader_get_last_error () || mono_class_has_failure (klass)) {
+       if (mono_class_has_failure (klass)) {
                if (klass->generic_class && !mono_class_is_valid_generic_instantiation (NULL, klass))
                        ADD_VERIFY_ERROR2 (ctx, g_strdup_printf ("Invalid generic instantiation of type %s.%s at 0x%04x", klass->name_space, klass->name, ctx->ip_offset), MONO_EXCEPTION_TYPE_LOAD);
                else
                        ADD_VERIFY_ERROR2 (ctx, g_strdup_printf ("Could not load type %s.%s at 0x%04x", klass->name_space, klass->name, ctx->ip_offset), MONO_EXCEPTION_TYPE_LOAD);
-               mono_loader_clear_error ();
                return FALSE;
        }
 
@@ -1020,9 +1020,8 @@ verifier_load_type (VerifyContext *ctx, int token, const char *opcode) {
                mono_error_cleanup (&error); /*FIXME don't swallow the error */
        }
 
-       if (!type || mono_loader_get_last_error ()) {
+       if (!type) {
                ADD_VERIFY_ERROR2 (ctx, g_strdup_printf ("Cannot load type from token 0x%08x for %s at 0x%04x", token, opcode, ctx->ip_offset), MONO_EXCEPTION_BAD_IMAGE);
-               mono_loader_clear_error ();
                return NULL;
        }
 
@@ -5016,7 +5015,7 @@ mono_method_verify (MonoMethod *method, int level)
        if (!ctx.valid)
                goto cleanup;
 
-       original_bb = bb = mono_basic_block_split (method, &error);
+       original_bb = bb = mono_basic_block_split (method, &error, ctx.header);
        if (!mono_error_ok (&error)) {
                ADD_VERIFY_ERROR (&ctx, g_strdup_printf ("Invalid branch target: %s", mono_error_get_message (&error)));
                mono_error_cleanup (&error);
index 6d5feb04e017d390c3a279bf372d1fff13cd8e0c..ce3c864090f6279345a817fbd51bb370d4d85b29 100755 (executable)
@@ -1,6 +1,13 @@
 count=100000
 mtest=for_loop
 monodir=$(top_builddir)
+mono=$(if $(MONO_EXECUTABLE),$(MONO_EXECUTABLE),mono)
+
+if HOST_WIN32
+PLATFORM_PATH_SEPARATOR=;
+else
+PLATFORM_PATH_SEPARATOR=:
+endif
 
 # This is needed for automake dependency generation
 libgc_libs=$(monodir)/libgc/libmonogc.la
@@ -39,9 +46,10 @@ CLASS=$(mcs_topdir)/class/lib/$(DEFAULT_PROFILE)
 RUNTIME_EXECUTABLE = $(if $(BOEHM),$(top_builddir)/mono/mini/mono-boehm,$(top_builddir)/runtime/mono-wrapper)
 
 MINI_RUNTIME = MONO_PATH=$(CLASS) $(RUNTIME_EXECUTABLE)
-RUNTIME_AOTCHECK = MONO_PATH=$(CLASS):. $(RUNTIME_EXECUTABLE)
+RUNTIME_AOTCHECK = MONO_PATH="$(CLASS)$(PLATFORM_PATH_SEPARATOR)." $(RUNTIME_EXECUTABLE)
 
-MCS = $(MINI_RUNTIME) $(mcs_topdir)/class/lib/build/mcs.exe -unsafe -nowarn:0162
+CSC = $(mcs_topdir)/class/lib/build/mcs.exe
+MCS = CSC_SDK_PATH_DISABLED= $(MINI_RUNTIME) $(CSC) -unsafe -nowarn:0162 -nologo -noconfig -r:$(CLASS)/mscorlib.dll -r:$(CLASS)/System.dll
 ILASM = $(MINI_RUNTIME) $(CLASS)/ilasm.exe
 
 AM_CFLAGS = \
@@ -297,13 +305,18 @@ x86_sources = \
        mini-x86.c              \
        mini-x86.h              \
        exceptions-x86.c        \
-       tramp-x86.c
+       tramp-x86.c     \
+       mini-x86-gsharedvt.c    \
+       tramp-x86-gsharedvt.c
 
 amd64_sources = \
        mini-amd64.c            \
        mini-amd64.h            \
        exceptions-amd64.c      \
-       tramp-amd64.c
+       tramp-amd64.c   \
+       mini-amd64-gsharedvt.c  \
+       mini-amd64-gsharedvt.h  \
+       tramp-amd64-gsharedvt.c
 
 ppc_sources = \
        mini-ppc.c              \
@@ -317,13 +330,17 @@ arm_sources = \
        mini-arm.h              \
        mini-arm-tls.h          \
        exceptions-arm.c        \
-       tramp-arm.c
+       tramp-arm.c     \
+       mini-arm-gsharedvt.c    \
+       tramp-arm-gsharedvt.c
 
 arm64_sources = \
        mini-arm64.c            \
        mini-arm64.h            \
        exceptions-arm64.c      \
-       tramp-arm64.c
+       tramp-arm64.c   \
+       mini-arm64-gsharedvt.c  \
+       tramp-arm64-gsharedvt.c
 
 mips_sources = \
        mini-mips.c             \
@@ -389,6 +406,8 @@ common_sources = \
        seq-points.h    \
        ir-emit.h               \
        method-to-ir.c          \
+       cfgdump.h               \
+       cfgdump.c               \
        decompose.c             \
        mini.h                  \
        version.h               \
@@ -418,6 +437,7 @@ common_sources = \
        graph.c                 \
        mini-codegen.c          \
        mini-exceptions.c       \
+       mini-exceptions-native-unwinder.c       \
        mini-trampolines.c      \
        branch-opts.c           \
        mini-generic-sharing.c  \
@@ -585,13 +605,13 @@ libmonoinclude_HEADERS = jit.h
 CSFLAGS = -unsafe -nowarn:0219,0169,0414,0649
 
 basic-simd.exe: basic-simd.cs TestDriver.dll
-       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:Mono.Simd.dll
+       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:$(CLASS)/Mono.Simd.dll
 
 nacl.exe: nacl.cs TestDriver.dll
-       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:Mono.Simd.dll
+       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:$(CLASS)/Mono.Simd.dll
 
 generics.exe: generics.cs TestDriver.dll generics-variant-types.dll
-       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:generics-variant-types.dll
+       $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll -r:generics-variant-types.dll -r:$(CLASS)/System.Core.dll
 
 %.exe: %.cs TestDriver.dll
        $(MCS) -out:$@ $(CSFLAGS) $< -r:TestDriver.dll
@@ -715,13 +735,13 @@ FULLAOT_LIBS = \
        Mono.Simd.dll
 
 # This currently only works on amd64/arm
-fullaotcheck: mono $(fullaot_regtests)
+fullaotcheck: $(mono) $(fullaot_regtests)
        rm -rf fullaot-tmp
        mkdir fullaot-tmp
-       $(MAKE) fullaot-libs AOT_FLAGS=full GSHAREDVT=$(GSHAREDVT)
+       $(MAKE) fullaot-libs AOT_FLAGS="full,$(MONO_FULLAOT_ADDITIONAL_ARGS)" GSHAREDVT=$(GSHAREDVT)
        cp $(regtests) $(fullaot_regtests) generics-variant-types.dll TestDriver.dll fullaot-tmp/
-       MONO_PATH=fullaot-tmp $(top_builddir)/runtime/mono-wrapper $(LLVM_AOT_RUNTIME_OPTS) $(GSHAREDVT_RUNTIME_OPTS) --aot=full fullaot-tmp/{generics-variant-types.dll,TestDriver.dll,*.exe} || exit 1
-       ln -s $$PWD/mono fullaot-tmp/
+       MONO_PATH=fullaot-tmp $(top_builddir)/runtime/mono-wrapper $(LLVM_AOT_RUNTIME_OPTS) $(GSHAREDVT_RUNTIME_OPTS) --aot="full,$(MONO_FULLAOT_ADDITIONAL_ARGS)" fullaot-tmp/{generics-variant-types.dll,TestDriver.dll,*.exe} || exit 1
+       ln -s $(if $(MONO_EXECUTABLE),$(MONO_EXECUTABLE),$$PWD/mono) fullaot-tmp/
        for i in $(fullaot_regtests); do echo $$i; MONO_PATH=fullaot-tmp $(top_builddir)/runtime/mono-wrapper --full-aot fullaot-tmp/$$i --exclude '!FULLAOT' $(ARCH_FULLAOT_EXCLUDE) || exit 1; done
 
 # This can run in parallel
@@ -730,7 +750,7 @@ fullaot-libs: $(patsubst %,fullaot-tmp/%.dylib,$(FULLAOT_LIBS))
 fullaot-tmp/%.dylib: $(CLASS)/%
        cp $(CLASS)/$* fullaot-tmp/
        mkdir fullaot-tmp/$*-tmp
-       MONO_PATH=fullaot-tmp/:$(CLASS) $(top_builddir)/runtime/mono-wrapper $(if $(GSHAREDVT),-O=gsharedvt) --aot=$(AOT_FLAGS),temp-path=fullaot-tmp/$*-tmp fullaot-tmp/$*
+       MONO_PATH="fullaot-tmp/$(PLATFORM_PATH_SEPARATOR)$(CLASS)" $(top_builddir)/runtime/mono-wrapper $(if $(GSHAREDVT),-O=gsharedvt) --aot=$(AOT_FLAGS),temp-path=fullaot-tmp/$*-tmp fullaot-tmp/$*
        rm -rf fullaot-tmp/$*-tmp
 
 llvmfullaotcheck:
@@ -741,7 +761,7 @@ llvmonly_regtests = $(fullaot_regtests) gshared.exe
 llvmonlycheck: mono $(llvmonly_regtests)
        rm -rf fullaot-tmp
        mkdir fullaot-tmp
-       $(MAKE) fullaot-libs AOT_FLAGS=llvmonly
+       $(MAKE) fullaot-libs AOT_FLAGS="llvmonly,$(MONO_FULLAOT_ADDITIONAL_ARGS)"
        cp $(llvmonly_regtests) generics-variant-types.dll TestDriver.dll fullaot-tmp/
        MONO_PATH=fullaot-tmp $(top_builddir)/runtime/mono-wrapper  --aot=llvmonly fullaot-tmp/{generics-variant-types.dll,TestDriver.dll,*.exe} || exit 1
        ln -s $$PWD/mono fullaot-tmp/
index 70e293d123d782331054c6abf1aa31b5916be2c3..318c4293d01da0b7c00f2b80c8beaaba4db9fb07 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc 
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -378,18 +379,87 @@ report_loader_error (MonoAotCompile *acfg, MonoError *error, const char *format,
 
 /* Wrappers around the image writer functions */
 
+#define MAX_SYMBOL_SIZE 256
+
+static inline const char *
+mangle_symbol (const char * symbol, char * mangled_symbol, gsize length)
+{
+       gsize needed_size = length;
+
+       g_assert (NULL != symbol);
+       g_assert (NULL != mangled_symbol);
+       g_assert (0 != length);
+
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+       if (symbol && '_' != symbol [0]) {
+               needed_size = g_snprintf (mangled_symbol, length, "_%s", symbol);
+       } else {
+               needed_size = g_snprintf (mangled_symbol, length, "%s", symbol);
+       }
+#else
+       needed_size = g_snprintf (mangled_symbol, length, "%s", symbol);
+#endif
+
+       g_assert (0 <= needed_size && needed_size < length);
+       return mangled_symbol;
+}
+
+static inline char *
+mangle_symbol_alloc (const char * symbol)
+{
+       g_assert (NULL != symbol);
+
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+       if (symbol && '_' != symbol [0]) {
+               return g_strdup_printf ("_%s", symbol);
+       }
+       else {
+               return g_strdup_printf ("%s", symbol);
+       }
+#else
+       return g_strdup_printf ("%s", symbol);
+#endif
+}
+
 static inline void
 emit_section_change (MonoAotCompile *acfg, const char *section_name, int subsection_index)
 {
        mono_img_writer_emit_section_change (acfg->w, section_name, subsection_index);
 }
 
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+
+static inline void
+emit_local_symbol (MonoAotCompile *acfg, const char *name, const char *end_label, gboolean func)
+{
+       const char * mangled_symbol_name = name;
+       char * mangled_symbol_name_alloc = NULL;
+
+       if (TRUE == func) {
+               mangled_symbol_name_alloc = mangle_symbol_alloc (name);
+               mangled_symbol_name = mangled_symbol_name_alloc;
+       }
+
+       if (name != mangled_symbol_name && 0 != g_strcasecmp (name, mangled_symbol_name)) {
+               mono_img_writer_emit_label (acfg->w, mangled_symbol_name);
+       }
+       mono_img_writer_emit_local_symbol (acfg->w, mangled_symbol_name, end_label, func);
+
+       if (NULL != mangled_symbol_name_alloc) {
+               g_free (mangled_symbol_name_alloc);
+       }
+}
+
+#else
+
 static inline void
 emit_local_symbol (MonoAotCompile *acfg, const char *name, const char *end_label, gboolean func) 
 { 
-       mono_img_writer_emit_local_symbol (acfg->w, name, end_label, func); 
+       mono_img_writer_emit_local_symbol (acfg->w, name, end_label, func);
 }
 
+#endif
+
 static inline void
 emit_label (MonoAotCompile *acfg, const char *name) 
 { 
@@ -506,12 +576,37 @@ emit_nacl_call_alignment (MonoAotCompile *acfg)
 }
 #endif
 
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+
+static G_GNUC_UNUSED void
+emit_global_inner (MonoAotCompile *acfg, const char *name, gboolean func)
+{
+       const char * mangled_symbol_name = name;
+       char * mangled_symbol_name_alloc = NULL;
+
+       mangled_symbol_name_alloc = mangle_symbol_alloc (name);
+       mangled_symbol_name = mangled_symbol_name_alloc;
+       
+       if (0 != g_strcasecmp (name, mangled_symbol_name)) {
+               mono_img_writer_emit_label (acfg->w, mangled_symbol_name);
+       }
+       mono_img_writer_emit_global (acfg->w, mangled_symbol_name, func);
+
+       if (NULL != mangled_symbol_name_alloc) {
+               g_free (mangled_symbol_name_alloc);
+       }
+}
+
+#else
+
 static G_GNUC_UNUSED void
 emit_global_inner (MonoAotCompile *acfg, const char *name, gboolean func)
 {
        mono_img_writer_emit_global (acfg->w, name, func);
 }
 
+#endif
+
 static void
 emit_global (MonoAotCompile *acfg, const char *name, gboolean func)
 {
@@ -519,7 +614,7 @@ emit_global (MonoAotCompile *acfg, const char *name, gboolean func)
                g_ptr_array_add (acfg->globals, g_strdup (name));
                mono_img_writer_emit_local_symbol (acfg->w, name, NULL, func);
        } else {
-               mono_img_writer_emit_global (acfg->w, name, func);
+               emit_global_inner (acfg, name, func);
        }
 }
 
@@ -533,7 +628,7 @@ emit_symbol_size (MonoAotCompile *acfg, const char *name, const char *end_label)
 static void
 emit_info_symbol (MonoAotCompile *acfg, const char *name)
 {
-       char symbol [256];
+       char symbol [MAX_SYMBOL_SIZE];
 
        if (acfg->llvm) {
                emit_label (acfg, name);
@@ -857,7 +952,330 @@ arch_init (MonoAotCompile *acfg)
 
 #ifdef TARGET_ARM64
 
-#include "../../../mono-extensions/mono/mini/aot-compiler-arm64.c"
+
+/* Load the contents of GOT_SLOT into dreg, clobbering ip0 */
+static void
+arm64_emit_load_got_slot (MonoAotCompile *acfg, int dreg, int got_slot)
+{
+       int offset;
+
+       g_assert (acfg->fp);
+       emit_unset_mode (acfg);
+       /* r16==ip0 */
+       offset = (int)(got_slot * sizeof (gpointer));
+#ifdef TARGET_MACH
+       /* clang's integrated assembler */
+       fprintf (acfg->fp, "adrp x16, %s@PAGE+%d\n", acfg->got_symbol, offset & 0xfffff000);
+       fprintf (acfg->fp, "add x16, x16, %s@PAGEOFF\n", acfg->got_symbol);
+       fprintf (acfg->fp, "ldr x%d, [x16, #%d]\n", dreg, offset & 0xfff);
+#else
+       /* Linux GAS */
+       fprintf (acfg->fp, "adrp x16, %s+%d\n", acfg->got_symbol, offset & 0xfffff000);
+       fprintf (acfg->fp, "add x16, x16, :lo12:%s\n", acfg->got_symbol);
+       fprintf (acfg->fp, "ldr x%d, [x16, %d]\n", dreg, offset & 0xfff);
+#endif
+}
+
+static void
+arm64_emit_objc_selector_ref (MonoAotCompile *acfg, guint8 *code, int index, int *code_size)
+{
+       int reg;
+
+       g_assert (acfg->fp);
+       emit_unset_mode (acfg);
+
+       /* ldr rt, target */
+       reg = arm_get_ldr_lit_reg (code);
+
+       fprintf (acfg->fp, "adrp x%d, L_OBJC_SELECTOR_REFERENCES_%d@PAGE\n", reg, index);
+       fprintf (acfg->fp, "add x%d, x%d, L_OBJC_SELECTOR_REFERENCES_%d@PAGEOFF\n", reg, reg, index);
+       fprintf (acfg->fp, "ldr x%d, [x%d]\n", reg, reg);
+
+       *code_size = 12;
+}
+
+static void
+arm64_emit_direct_call (MonoAotCompile *acfg, const char *target, gboolean external, gboolean thumb, MonoJumpInfo *ji, int *call_size)
+{
+       g_assert (acfg->fp);
+       emit_unset_mode (acfg);
+       if (ji && ji->relocation == MONO_R_ARM64_B) {
+               fprintf (acfg->fp, "b %s\n", target);
+       } else {
+               if (ji)
+                       g_assert (ji->relocation == MONO_R_ARM64_BL);
+               fprintf (acfg->fp, "bl %s\n", target);
+       }
+       *call_size = 4;
+}
+
+static void
+arm64_emit_got_access (MonoAotCompile *acfg, guint8 *code, int got_slot, int *code_size)
+{
+       int reg;
+
+       /* ldr rt, target */
+       reg = arm_get_ldr_lit_reg (code);
+       arm64_emit_load_got_slot (acfg, reg, got_slot);
+       *code_size = 12;
+}
+
+static void
+arm64_emit_plt_entry (MonoAotCompile *acfg, const char *got_symbol, int offset, int info_offset)
+{
+       arm64_emit_load_got_slot (acfg, ARMREG_R16, offset / sizeof (gpointer));
+       fprintf (acfg->fp, "br x16\n");
+       /* Used by mono_aot_get_plt_info_offset () */
+       fprintf (acfg->fp, "%s %d\n", acfg->inst_directive, info_offset);
+}
+
+static void
+arm64_emit_tramp_page_common_code (MonoAotCompile *acfg, int pagesize, int arg_reg, int *size)
+{
+       guint8 buf [256];
+       guint8 *code;
+       int imm;
+
+       /* The common code */
+       code = buf;
+       imm = pagesize;
+       /* The trampoline address is in IP0 */
+       arm_movzx (code, ARMREG_IP1, imm & 0xffff, 0);
+       arm_movkx (code, ARMREG_IP1, (imm >> 16) & 0xffff, 16);
+       /* Compute the data slot address */
+       arm_subx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+       /* Trampoline argument */
+       arm_ldrx (code, arg_reg, ARMREG_IP0, 0);
+       /* Address */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 8);
+       arm_brx (code, ARMREG_IP0);
+
+       /* Emit it */
+       emit_code_bytes (acfg, buf, code - buf);
+
+       *size = code - buf;
+}
+
+static void
+arm64_emit_tramp_page_specific_code (MonoAotCompile *acfg, int pagesize, int common_tramp_size, int specific_tramp_size)
+{
+       guint8 buf [256];
+       guint8 *code;
+       int i, count;
+
+       count = (pagesize - common_tramp_size) / specific_tramp_size;
+       for (i = 0; i < count; ++i) {
+               code = buf;
+               arm_adrx (code, ARMREG_IP0, code);
+               /* Branch to the generic code */
+               arm_b (code, code - 4 - (i * specific_tramp_size) - common_tramp_size);
+               /* This has to be 2 pointers long */
+               arm_nop (code);
+               arm_nop (code);
+               g_assert (code - buf == specific_tramp_size);
+               emit_code_bytes (acfg, buf, code - buf);
+       }
+}
+
+static void
+arm64_emit_specific_trampoline_pages (MonoAotCompile *acfg)
+{
+       guint8 buf [128];
+       guint8 *code;
+       guint8 *labels [16];
+       int common_tramp_size;
+       int specific_tramp_size = 2 * 8;
+       int imm, pagesize;
+       char symbol [128];
+
+       if (!acfg->aot_opts.use_trampolines_page)
+               return;
+
+#ifdef TARGET_MACH
+       /* Have to match the target pagesize */
+       pagesize = 16384;
+#else
+       pagesize = mono_pagesize ();
+#endif
+       acfg->tramp_page_size = pagesize;
+
+       /* The specific trampolines */
+       sprintf (symbol, "%sspecific_trampolines_page", acfg->user_symbol_prefix);
+       emit_alignment (acfg, pagesize);
+       emit_global (acfg, symbol, TRUE);
+       emit_label (acfg, symbol);
+
+       /* The common code */
+       arm64_emit_tramp_page_common_code (acfg, pagesize, ARMREG_IP1, &common_tramp_size);
+       acfg->tramp_page_code_offsets [MONO_AOT_TRAMP_SPECIFIC] = common_tramp_size;
+
+       arm64_emit_tramp_page_specific_code (acfg, pagesize, common_tramp_size, specific_tramp_size);
+
+       /* The rgctx trampolines */
+       /* These are the same as the specific trampolines, but they load the argument into MONO_ARCH_RGCTX_REG */
+       sprintf (symbol, "%srgctx_trampolines_page", acfg->user_symbol_prefix);
+       emit_alignment (acfg, pagesize);
+       emit_global (acfg, symbol, TRUE);
+       emit_label (acfg, symbol);
+
+       /* The common code */
+       arm64_emit_tramp_page_common_code (acfg, pagesize, MONO_ARCH_RGCTX_REG, &common_tramp_size);
+       acfg->tramp_page_code_offsets [MONO_AOT_TRAMP_STATIC_RGCTX] = common_tramp_size;
+
+       arm64_emit_tramp_page_specific_code (acfg, pagesize, common_tramp_size, specific_tramp_size);
+
+       /* The gsharedvt arg trampolines */
+       /* These are the same as the specific trampolines */
+       sprintf (symbol, "%sgsharedvt_arg_trampolines_page", acfg->user_symbol_prefix);
+       emit_alignment (acfg, pagesize);
+       emit_global (acfg, symbol, TRUE);
+       emit_label (acfg, symbol);
+
+       arm64_emit_tramp_page_common_code (acfg, pagesize, ARMREG_IP1, &common_tramp_size);
+       acfg->tramp_page_code_offsets [MONO_AOT_TRAMP_GSHAREDVT_ARG] = common_tramp_size;
+
+       arm64_emit_tramp_page_specific_code (acfg, pagesize, common_tramp_size, specific_tramp_size);
+
+       /* The IMT trampolines */
+       sprintf (symbol, "%simt_trampolines_page", acfg->user_symbol_prefix);
+       emit_alignment (acfg, pagesize);
+       emit_global (acfg, symbol, TRUE);
+       emit_label (acfg, symbol);
+
+       code = buf;
+       imm = pagesize;
+       /* The trampoline address is in IP0 */
+       arm_movzx (code, ARMREG_IP1, imm & 0xffff, 0);
+       arm_movkx (code, ARMREG_IP1, (imm >> 16) & 0xffff, 16);
+       /* Compute the data slot address */
+       arm_subx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+       /* Trampoline argument */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_IP0, 0);
+
+       /* Same as arch_emit_imt_thunk () */
+       labels [0] = code;
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 0);
+       arm_cmpx (code, ARMREG_IP0, MONO_ARCH_RGCTX_REG);
+       labels [1] = code;
+       arm_bcc (code, ARMCOND_EQ, 0);
+
+       /* End-of-loop check */
+       labels [2] = code;
+       arm_cbzx (code, ARMREG_IP0, 0);
+
+       /* Loop footer */
+       arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, 2 * 8);
+       arm_b (code, labels [0]);
+
+       /* Match */
+       mono_arm_patch (labels [1], code, MONO_R_ARM64_BCC);
+       /* Load vtable slot addr */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 8);
+       /* Load vtable slot */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 0);
+       arm_brx (code, ARMREG_IP0);
+
+       /* No match */
+       mono_arm_patch (labels [2], code, MONO_R_ARM64_CBZ);
+       /* Load fail addr */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 8);
+       arm_brx (code, ARMREG_IP0);
+
+       emit_code_bytes (acfg, buf, code - buf);
+
+       common_tramp_size = code - buf;
+       acfg->tramp_page_code_offsets [MONO_AOT_TRAMP_IMT_THUNK] = common_tramp_size;
+
+       arm64_emit_tramp_page_specific_code (acfg, pagesize, common_tramp_size, specific_tramp_size);
+}
+
+static void
+arm64_emit_specific_trampoline (MonoAotCompile *acfg, int offset, int *tramp_size)
+{
+       /* Load argument from second GOT slot */
+       arm64_emit_load_got_slot (acfg, ARMREG_R17, offset + 1);
+       /* Load generic trampoline address from first GOT slot */
+       arm64_emit_load_got_slot (acfg, ARMREG_R16, offset);
+       fprintf (acfg->fp, "br x16\n");
+       *tramp_size = 7 * 4;
+}
+
+static void
+arm64_emit_unbox_trampoline (MonoAotCompile *acfg, MonoCompile *cfg, MonoMethod *method, const char *call_target)
+{
+       emit_unset_mode (acfg);
+       fprintf (acfg->fp, "add x0, x0, %d\n", (int)(sizeof (MonoObject)));
+       fprintf (acfg->fp, "b %s\n", call_target);
+}
+
+static void
+arm64_emit_static_rgctx_trampoline (MonoAotCompile *acfg, int offset, int *tramp_size)
+{
+       /* Similar to the specific trampolines, but use the rgctx reg instead of ip1 */
+
+       /* Load argument from first GOT slot */
+       arm64_emit_load_got_slot (acfg, MONO_ARCH_RGCTX_REG, offset);
+       /* Load generic trampoline address from second GOT slot */
+       arm64_emit_load_got_slot (acfg, ARMREG_R16, offset + 1);
+       fprintf (acfg->fp, "br x16\n");
+       *tramp_size = 7 * 4;
+}
+
+static void
+arm64_emit_imt_thunk (MonoAotCompile *acfg, int offset, int *tramp_size)
+{
+       guint8 buf [128];
+       guint8 *code, *labels [16];
+
+       /* Load parameter from GOT slot into ip1 */
+       arm64_emit_load_got_slot (acfg, ARMREG_R17, offset);
+
+       code = buf;
+       labels [0] = code;
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 0);
+       arm_cmpx (code, ARMREG_IP0, MONO_ARCH_RGCTX_REG);
+       labels [1] = code;
+       arm_bcc (code, ARMCOND_EQ, 0);
+
+       /* End-of-loop check */
+       labels [2] = code;
+       arm_cbzx (code, ARMREG_IP0, 0);
+
+       /* Loop footer */
+       arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, 2 * 8);
+       arm_b (code, labels [0]);
+
+       /* Match */
+       mono_arm_patch (labels [1], code, MONO_R_ARM64_BCC);
+       /* Load vtable slot addr */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 8);
+       /* Load vtable slot */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 0);
+       arm_brx (code, ARMREG_IP0);
+
+       /* No match */
+       mono_arm_patch (labels [2], code, MONO_R_ARM64_CBZ);
+       /* Load fail addr */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP1, 8);
+       arm_brx (code, ARMREG_IP0);
+
+       emit_code_bytes (acfg, buf, code - buf);
+
+       *tramp_size = code - buf + (3 * 4);
+}
+
+static void
+arm64_emit_gsharedvt_arg_trampoline (MonoAotCompile *acfg, int offset, int *tramp_size)
+{
+       /* Similar to the specific trampolines, but the address is in the second slot */
+       /* Load argument from first GOT slot */
+       arm64_emit_load_got_slot (acfg, ARMREG_R17, offset);
+       /* Load generic trampoline address from second GOT slot */
+       arm64_emit_load_got_slot (acfg, ARMREG_R16, offset + 1);
+       fprintf (acfg->fp, "br x16\n");
+       *tramp_size = 7 * 4;
+}
+
 
 #endif
 
@@ -1038,8 +1456,8 @@ static void
 arch_emit_objc_selector_ref (MonoAotCompile *acfg, guint8 *code, int index, int *code_size)
 {
 #if defined(TARGET_ARM)
-       char symbol1 [256];
-       char symbol2 [256];
+       char symbol1 [MAX_SYMBOL_SIZE];
+       char symbol2 [MAX_SYMBOL_SIZE];
        int lindex = acfg->objc_selector_index_2 ++;
 
        /* Emit ldr.imm/b */
@@ -4966,7 +5384,7 @@ emit_and_reloc_code (MonoAotCompile *acfg, MonoMethod *method, guint8 *code, gui
        GPtrArray *patches;
        MonoJumpInfo *patch_info;
        MonoDebugSourceLocation **locs = NULL;
-       gboolean skip;
+       gboolean skip, prologue_end = FALSE;
 #ifdef MONO_ARCH_AOT_SUPPORTED
        gboolean direct_call, external_call;
        guint32 got_slot;
@@ -5001,10 +5419,16 @@ emit_and_reloc_code (MonoAotCompile *acfg, MonoMethod *method, guint8 *code, gui
                if (locs && locs [i]) {
                        MonoDebugSourceLocation *loc = locs [i];
                        int findex;
+                       const char *options;
 
                        findex = get_file_index (acfg, loc->source_file);
                        emit_unset_mode (acfg);
-                       fprintf (acfg->fp, ".loc %d %d 0\n", findex, loc->row);
+                       if (!prologue_end)
+                               options = " prologue_end";
+                       else
+                               options = "";
+                       prologue_end = TRUE;
+                       fprintf (acfg->fp, ".loc %d %d 0%s\n", findex, loc->row, options);
                        mono_debug_symfile_free_location (loc);
                }
 
@@ -5232,6 +5656,11 @@ get_debug_sym (MonoMethod *method, const char *prefix, GHashTable *cache)
                prefix = "_";
 #endif
 
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+       char adjustedPrefix [MAX_SYMBOL_SIZE];
+       prefix = mangle_symbol (prefix, adjustedPrefix, G_N_ELEMENTS (adjustedPrefix));
+#endif
+
        len = strlen (name1);
        name2 = (char *)malloc (strlen (prefix) + len + 16);
        memcpy (name2, prefix, strlen (prefix));
@@ -6045,7 +6474,11 @@ get_plt_entry_debug_sym (MonoAotCompile *acfg, MonoJumpInfo *ji, GHashTable *cac
                /* Need to add a prefix to create unique symbols */
                prefix = g_strdup_printf ("plt_%s_", acfg->assembly_name_sym);
        } else {
+#if defined(TARGET_WIN32) && defined(TARGET_X86)
+               prefix = mangle_symbol_alloc ("plt_");
+#else
                prefix = g_strdup ("plt_");
+#endif
        }
 
        switch (ji->type) {
@@ -6213,9 +6646,9 @@ emit_plt (MonoAotCompile *acfg)
 static G_GNUC_UNUSED void
 emit_trampoline_full (MonoAotCompile *acfg, int got_offset, MonoTrampInfo *info, gboolean emit_tinfo)
 {
-       char start_symbol [256];
-       char end_symbol [256];
-       char symbol [256];
+       char start_symbol [MAX_SYMBOL_SIZE];
+       char end_symbol [MAX_SYMBOL_SIZE];
+       char symbol [MAX_SYMBOL_SIZE];
        guint32 buf_size, info_offset;
        MonoJumpInfo *patch_info;
        guint8 *buf, *p;
@@ -6307,7 +6740,7 @@ emit_trampoline_full (MonoAotCompile *acfg, int got_offset, MonoTrampInfo *info,
 
        /* Emit debug info */
        if (unwind_ops) {
-               char symbol2 [256];
+               char symbol2 [MAX_SYMBOL_SIZE];
 
                sprintf (symbol, "%s", name);
                sprintf (symbol2, "%snamed_%s", acfg->temp_prefix, name);
@@ -6326,8 +6759,8 @@ emit_trampoline (MonoAotCompile *acfg, int got_offset, MonoTrampInfo *info)
 static void
 emit_trampolines (MonoAotCompile *acfg)
 {
-       char symbol [256];
-       char end_symbol [256];
+       char symbol [MAX_SYMBOL_SIZE];
+       char end_symbol [MAX_SYMBOL_SIZE];
        int i, tramp_got_offset;
        int ntype;
 #ifdef MONO_ARCH_HAVE_FULL_AOT_TRAMPOLINES
@@ -6670,6 +7103,15 @@ wrap_path (gchar * path)
        return clean;
 }
 
+// Duplicate a char range and add it to a ptrarray, but only if it is nonempty
+static void
+ptr_array_add_range_if_nonempty(GPtrArray *args, gchar const *start, gchar const *end)
+{
+       ptrdiff_t len = end-start;
+       if (len > 0)
+               g_ptr_array_add (args, g_strndup (start, len));
+}
+
 static GPtrArray *
 mono_aot_split_options (const char *aot_options)
 {
@@ -6725,6 +7167,7 @@ mono_aot_split_options (const char *aot_options)
 
        next:
                aot_options++;
+       restart:
                // If the next character is end of string, then process the last option.
                if (*(aot_options) == '\0') {
                        end_of_string = TRUE;
@@ -6733,11 +7176,11 @@ mono_aot_split_options (const char *aot_options)
                continue;
 
        new_opt:
-               g_ptr_array_add (args, g_strndup (opt_start, aot_options - opt_start));
+               ptr_array_add_range_if_nonempty (args, opt_start, aot_options);
                opt_start = ++aot_options;
                if (end_of_string)
                        break;
-               goto next;
+               goto restart; // Check for null and continue loop
        }
 
        return args;
@@ -7207,8 +7650,6 @@ compile_method (MonoAotCompile *acfg, MonoMethod *method)
        cfg = mini_method_compile (method, acfg->opts, mono_get_root_domain (), flags, 0, index);
        mono_time_track_end (&mono_jit_stats.jit_time, jit_timer);
 
-       mono_loader_clear_error ();
-
        if (cfg->exception_type == MONO_EXCEPTION_GENERIC_SHARING_FAILED) {
                if (acfg->aot_opts.print_skipped_methods)
                        printf ("Skip (gshared failure): %s (%s)\n", mono_method_get_full_name (method), cfg->exception_message);
@@ -7527,7 +7968,10 @@ compile_thread_main (gpointer *user_data)
        GPtrArray *methods = (GPtrArray *)user_data [2];
        int i;
 
-       mono_thread_attach (domain);
+       MonoError error;
+       MonoThread *thread = mono_thread_attach (domain);
+       mono_thread_set_name_internal (thread->internal_thread, mono_string_new (mono_get_root_domain (), "AOT compiler"), TRUE, &error);
+       mono_error_assert_ok (&error);
 
        for (i = 0; i < methods->len; ++i)
                compile_method (acfg, (MonoMethod *)g_ptr_array_index (methods, i));
@@ -8062,7 +8506,7 @@ emit_code (MonoAotCompile *acfg)
 {
        int oindex, i, prev_index;
        gboolean saved_unbox_info = FALSE;
-       char symbol [256];
+       char symbol [MAX_SYMBOL_SIZE];
 
        if (acfg->aot_opts.llvm_only)
                return;
@@ -8183,6 +8627,7 @@ emit_code (MonoAotCompile *acfg)
         * To work around linker issues, we emit a table of branches, and disassemble them at runtime.
         * This is PIE code, and the linker can update it if needed.
         */
+       
        sprintf (symbol, "method_addresses");
        emit_section_change (acfg, ".text", 1);
        emit_alignment_code (acfg, 8);
@@ -8199,11 +8644,11 @@ emit_code (MonoAotCompile *acfg)
                if (acfg->cfgs [i]) {
                        if (acfg->aot_opts.llvm_only && acfg->cfgs [i]->compile_llvm)
                                /* Obtained by calling a generated function in the LLVM image */
-                               arch_emit_direct_call (acfg, "method_addresses", FALSE, FALSE, NULL, &call_size);
+                               arch_emit_direct_call (acfg, symbol, FALSE, FALSE, NULL, &call_size);
                        else
                                arch_emit_direct_call (acfg, acfg->cfgs [i]->asm_symbol, FALSE, acfg->thumb_mixed && acfg->cfgs [i]->compile_llvm, NULL, &call_size);
                } else {
-                       arch_emit_direct_call (acfg, "method_addresses", FALSE, FALSE, NULL, &call_size);
+                       arch_emit_direct_call (acfg, symbol, FALSE, FALSE, NULL, &call_size);
                }
 #endif
        }
@@ -8928,7 +9373,7 @@ emit_got_info (MonoAotCompile *acfg, gboolean llvm)
 static void
 emit_got (MonoAotCompile *acfg)
 {
-       char symbol [256];
+       char symbol [MAX_SYMBOL_SIZE];
 
        if (acfg->aot_opts.llvm_only)
                return;
@@ -9127,7 +9572,7 @@ init_aot_file_info (MonoAotCompile *acfg, MonoAotFileInfo *info)
 static void
 emit_aot_file_info (MonoAotCompile *acfg, MonoAotFileInfo *info)
 {
-       char symbol [256];
+       char symbol [MAX_SYMBOL_SIZE];
        int i, sindex;
        const char **symbols;
 
@@ -9288,7 +9733,7 @@ emit_file_info (MonoAotCompile *acfg)
        init_aot_file_info (acfg, info);
 
        if (acfg->aot_opts.static_link) {
-               char symbol [256];
+               char symbol [MAX_SYMBOL_SIZE];
                char *p;
 
                /*
@@ -9544,7 +9989,6 @@ compile_asm (MonoAotCompile *acfg)
 #define AS_OPTIONS "--64"
 #elif defined(TARGET_POWERPC64)
 #define AS_OPTIONS "-a64 -mppc64"
-#define LD_OPTIONS "-m elf64ppc"
 #elif defined(sparc) && SIZEOF_VOID_P == 8
 #define AS_OPTIONS "-xarch=v9"
 #elif defined(TARGET_X86) && defined(TARGET_MACH) && !defined(__native_client_codegen__)
@@ -9565,22 +10009,30 @@ compile_asm (MonoAotCompile *acfg)
 #define AS_NAME "as"
 #endif
 
-#ifndef LD_OPTIONS
-#define LD_OPTIONS ""
-#endif
-
 #if defined(sparc)
-#define LD_NAME "ld -shared -G"
+#define LD_NAME "ld"
+#define LD_OPTIONS "-shared -G"
 #elif defined(__ppc__) && defined(TARGET_MACH)
-#define LD_NAME "gcc -dynamiclib"
+#define LD_NAME "gcc"
+#define LD_OPTIONS "-dynamiclib"
 #elif defined(TARGET_AMD64) && defined(TARGET_MACH)
-#define LD_NAME "clang --shared"
+#define LD_NAME "clang"
+#define LD_OPTIONS "--shared"
 #elif defined(TARGET_WIN32) && !defined(TARGET_ANDROID)
-#define LD_NAME "gcc -shared --dll"
+#define LD_NAME "gcc"
+#define LD_OPTIONS "-shared"
 #elif defined(TARGET_X86) && defined(TARGET_MACH) && !defined(__native_client_codegen__)
-#define LD_NAME "clang -m32 -dynamiclib"
+#define LD_NAME "clang"
+#define LD_OPTIONS "-m32 -dynamiclib"
 #elif defined(TARGET_ARM) && !defined(TARGET_ANDROID)
-#define LD_NAME "gcc --shared"
+#define LD_NAME "gcc"
+#define LD_OPTIONS "--shared"
+#elif defined(TARGET_POWERPC64)
+#define LD_OPTIONS "-m elf64ppc"
+#endif
+
+#ifndef LD_OPTIONS
+#define LD_OPTIONS ""
 #endif
 
        if (acfg->aot_opts.asm_only) {
@@ -9656,10 +10108,11 @@ compile_asm (MonoAotCompile *acfg)
                ld_flags = g_strdup_printf ("%s %s", ld_flags, "-lstdc++");
 
 #ifdef LD_NAME
-       command = g_strdup_printf ("%s -o %s %s %s %s", LD_NAME,
+       command = g_strdup_printf ("%s%s %s -o %s %s %s %s", tool_prefix, LD_NAME, LD_OPTIONS,
                wrap_path (tmp_outfile_name), wrap_path (llvm_ofile),
                wrap_path (g_strdup_printf ("%s.o", acfg->tmpfname)), ld_flags);
 #else
+       // Default (linux)
        command = g_strdup_printf ("\"%sld\" %s -shared -o %s %s %s %s", tool_prefix, LD_OPTIONS,
                wrap_path (tmp_outfile_name), wrap_path (llvm_ofile),
                wrap_path (g_strdup_printf ("%s.o", acfg->tmpfname)), ld_flags);
@@ -9697,7 +10150,13 @@ compile_asm (MonoAotCompile *acfg)
        }
 #endif
 
-       rename (tmp_outfile_name, outfile_name);
+       if (0 != rename (tmp_outfile_name, outfile_name)) {
+               if (G_FILE_ERROR_EXIST == g_file_error_from_errno (errno)) {
+                       /* Since we are rebuilding the module we need to be able to replace any old copies. Remove old file and retry rename operation. */
+                       unlink (outfile_name);
+                       rename (tmp_outfile_name, outfile_name);
+               }
+       }
 
 #if defined(TARGET_MACH)
        command = g_strdup_printf ("dsymutil \"%s\"", outfile_name);
@@ -10092,7 +10551,7 @@ mono_compile_assembly (MonoAssembly *ass, guint32 opts, const char *aot_options)
 
        //acfg->aot_opts.print_skipped_methods = TRUE;
 
-#if !defined(ENABLE_GSHAREDVT)
+#if !defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
        if (opts & MONO_OPT_GSHAREDVT) {
                aot_printerrf (acfg, "-O=gsharedvt not supported on this platform.\n");
                return 1;
@@ -10107,15 +10566,17 @@ mono_compile_assembly (MonoAssembly *ass, guint32 opts, const char *aot_options)
 #endif
 
        if (acfg->aot_opts.llvm_only) {
-#ifndef ENABLE_GSHAREDVT
-               aot_printerrf (acfg, "--aot=llvmonly requires a runtime compiled with --enable-gsharedvt.\n");
+#ifndef MONO_ARCH_GSHAREDVT_SUPPORTED
+               aot_printerrf (acfg, "--aot=llvmonly requires a runtime that supports gsharedvt.\n");
                return 1;
 #endif
        }
 
-#if defined(ENABLE_GSHAREDVT) && defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
-       acfg->opts |= MONO_OPT_GSHAREDVT;
-       opts |= MONO_OPT_GSHAREDVT;
+#if defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
+       if (acfg->aot_opts.llvm_only || mono_aot_mode_is_full (&acfg->aot_opts)) {
+               acfg->opts |= MONO_OPT_GSHAREDVT;
+               opts |= MONO_OPT_GSHAREDVT;
+       }
 #endif
 
        if (opts & MONO_OPT_GSHAREDVT)
@@ -10329,13 +10790,11 @@ mono_compile_assembly (MonoAssembly *ass, guint32 opts, const char *aot_options)
                }
        }
 
-       if (acfg->aot_opts.dwarf_debug && acfg->aot_opts.asm_only && acfg->aot_opts.gnu_asm) {
+       if (acfg->aot_opts.dwarf_debug && acfg->aot_opts.gnu_asm) {
                /*
                 * CLANG supports GAS .file/.loc directives, so emit line number information this way
-                * FIXME: CLANG only emits line number info for .loc directives followed by assembly, not
-                * .byte directives.
                 */
-               //acfg->gas_line_numbers = TRUE;
+               acfg->gas_line_numbers = TRUE;
        }
 
        if ((!acfg->aot_opts.nodebug || acfg->aot_opts.dwarf_debug) && acfg->has_jitted_code) {
@@ -10343,7 +10802,7 @@ mono_compile_assembly (MonoAssembly *ass, guint32 opts, const char *aot_options)
                        aot_printerrf (acfg, "The dwarf AOT option requires the --debug option.\n");
                        return 1;
                }
-               acfg->dwarf = mono_dwarf_writer_create (acfg->w, NULL, 0, FALSE, !acfg->gas_line_numbers);
+               acfg->dwarf = mono_dwarf_writer_create (acfg->w, NULL, 0, !acfg->gas_line_numbers);
        }
 
        if (acfg->w)
index 93756b108b33cb4402a0ca57601aa8b0bb9a25cc..d3f3cf2e952c82b946e69b7a834082609d318d2e 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc.
  * Copyright 2011 Xamarin, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -1986,7 +1987,10 @@ load_aot_module (MonoAssembly *assembly, gpointer user_data)
                                mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_AOT, "AOT module '%s' not found: %s\n", aot_name, err);
                                g_free (err);
 
-                               aot_name = g_strdup_printf ("%s/mono/aot-cache/%s/%s%s", mono_assembly_getrootdir(), MONO_ARCHITECTURE, g_path_get_basename (assembly->image->name), MONO_SOLIB_EXT);
+                               g_free (aot_name);
+                               char *basename = g_path_get_basename (assembly->image->name);
+                               aot_name = g_strdup_printf ("%s/mono/aot-cache/%s/%s%s", mono_assembly_getrootdir(), MONO_ARCHITECTURE, basename, MONO_SOLIB_EXT);
+                               g_free (basename);
                                sofile = mono_dl_open (aot_name, MONO_DL_LAZY, &err);
                                if (!sofile) {
                                        mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_AOT, "AOT module '%s' not found: %s\n", aot_name, err);
@@ -3056,7 +3060,7 @@ decode_exception_debug_info (MonoAotModule *amodule, MonoDomain *domain,
                        mono_error_cleanup (&error); /* FIXME don't swallow the error */
                }
 
-               gi->generic_sharing_context = g_new0 (MonoGenericSharingContext, 1);
+               gi->generic_sharing_context = alloc0_jit_info_data (domain, sizeof (MonoGenericSharingContext), async);
                if (decode_value (p, &p)) {
                        /* gsharedvt */
                        MonoGenericSharingContext *gsctx = gi->generic_sharing_context;
@@ -5218,7 +5222,9 @@ get_new_trampoline_from_page (int tramp_type)
                /* allocate two contiguous pages of memory: the first page will contain the data (like a local constant pool)
                 * while the second will contain the trampolines.
                 */
-               ret = vm_allocate (mach_task_self (), &addr, psize * 2, VM_FLAGS_ANYWHERE);
+               do {
+                       ret = vm_allocate (mach_task_self (), &addr, psize * 2, VM_FLAGS_ANYWHERE);
+               } while (ret == KERN_ABORTED);
                if (ret != KERN_SUCCESS) {
                        g_error ("Cannot allocate memory for trampolines: %d", ret);
                        break;
index a75bab23586eab4d4d92fadbde33c865897c48b0..cad20a06b24c5662be9729fd1cc30f83d87b6a1f 100644 (file)
@@ -33,23 +33,6 @@ mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
 
 #endif
 
-#if defined(MONO_ARCH_GSHAREDVT_SUPPORTED) && !defined(ENABLE_GSHAREDVT)
-
-gboolean
-mono_arch_gsharedvt_sig_supported (MonoMethodSignature *sig)
-{
-       return FALSE;
-}
-
-gpointer
-mono_arch_get_gsharedvt_call_info (gpointer addr, MonoMethodSignature *normal_sig, MonoMethodSignature *gsharedvt_sig, gboolean gsharedvt_in, gint32 vcall_offset, gboolean calli)
-{
-       NOT_IMPLEMENTED;
-       return NULL;
-}
-
-#endif
-
 #ifndef MONO_ARCH_HAVE_DECOMPOSE_OPTS
 void
 mono_arch_decompose_opts (MonoCompile *cfg, MonoInst *ins)
index c6a23620c5676565fe57615b1b48f56beb2a8e2e..15cd67d60c69901a2fbee50eb36f1f13ed91911e 100644 (file)
@@ -2,6 +2,7 @@ using System;
 using System.Reflection;
 
 /*
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  * Regression tests for the mono JIT.
  *
  * Each test needs to be of the form:
index 1a4ea53fe1f9ecfa48455f4961f6e1c8f1283639..ca8289b81c8313619b3f5c3e5fec193c4a503298 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2005 Ximian, Inc.  http://www.ximian.com
  * Copyright 2011 Xamarin Inc.  http://www.xamarin.com
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
  #include "mini.h"
 
@@ -248,7 +249,8 @@ mono_replace_ins (MonoCompile *cfg, MonoBasicBlock *bb, MonoInst *ins, MonoInst
                bb->has_array_access |= first_bb->has_array_access;
 
                /* Delete the links between the original bb and its successors */
-               tmp_bblocks = bb->out_bb;
+               tmp_bblocks = mono_mempool_alloc0 (cfg->mempool, sizeof (MonoBasicBlock*) * bb->out_count);
+               memcpy (tmp_bblocks, bb->out_bb, sizeof (MonoBasicBlock*) * bb->out_count);
                count = bb->out_count;
                for (i = 0; i < count; ++i)
                        mono_unlink_bblock (cfg, bb, tmp_bblocks [i]);
diff --git a/mono/mini/cfgdump.c b/mono/mini/cfgdump.c
new file mode 100644 (file)
index 0000000..7b9cfd3
--- /dev/null
@@ -0,0 +1,556 @@
+/*
+ * Copyright (C) 2016 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+/* inspired by BinaryGraphPrinter.java of Graal */
+
+#include "mini.h"
+
+#if !defined(DISABLE_LOGGING) && !defined(DISABLE_JIT) && !defined(HOST_WIN32)
+
+#include <glib.h>
+#include <mono/metadata/class-internals.h>
+
+#include <sys/socket.h>
+#include <sys/types.h>
+#include <netinet/in.h>
+#include <netdb.h>
+#include <string.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <errno.h>
+#include <arpa/inet.h>
+#include <errno.h>
+
+#if 0
+#define CFG_DEBUG
+#endif
+
+
+#ifdef CFG_DEBUG
+
+#ifdef HAVE_C99_SUPPORT
+#define cfg_debug(format, ...) g_debug(format, __VA_ARGS__)
+#else
+#define cfg_debug(...) g_debug(__VA_ARGS__)
+#endif
+
+#else
+
+#ifdef HAVE_C99_SUPPORT
+#define cfg_debug(format, ...) do {} while (0)
+#else
+#define cfg_debug(...) do {} while (0)
+#endif
+
+#endif
+
+static ConstantPoolEntry*
+create_cp_entry (MonoCompile *cfg, void *data, pool_type pt)
+{
+       ConstantPoolEntry *entry = (ConstantPoolEntry *) mono_mempool_alloc0 (cfg->mempool, sizeof (ConstantPoolEntry));
+       entry->pt = pt;
+       entry->data = data;
+       return entry;
+}
+
+static void write_pool (MonoCompile *cfg, ConstantPoolEntry *entry);
+
+static int
+create_socket (const char *hostname, const int port)
+{
+    int sockfd = 0;
+    struct sockaddr_in serv_addr;
+
+    if ((sockfd = socket (AF_INET, SOCK_STREAM, 0)) < 0) {
+               g_warning ("cfg_dump: could not create socket");
+        return -1;
+    }
+
+    serv_addr.sin_family = AF_INET;
+    serv_addr.sin_port = htons (port);
+    serv_addr.sin_addr.s_addr = inet_addr (hostname);
+
+    if (connect (sockfd, (struct sockaddr *)&serv_addr, sizeof(serv_addr)) < 0) {
+        g_warning ("cfg_dump: Connect Failed: %s", strerror (errno));
+        return -2;
+    }
+
+       return sockfd;
+}
+
+static void
+write_byte (MonoCompile *cfg, unsigned char b)
+{
+       write (cfg->gdump_ctx->fd, &b, 1);
+}
+
+static void
+write_short (MonoCompile *cfg, short s)
+{
+       short swap = htons (s);
+       write (cfg->gdump_ctx->fd, &swap, 2);
+}
+
+static void
+write_int (MonoCompile *cfg, int v)
+{
+       int swap = htonl (v);
+       write (cfg->gdump_ctx->fd, &swap, 4);
+}
+
+static void
+write_string (MonoCompile *cfg, const char *str)
+{
+       size_t len = strnlen (str, 0x2000);
+       write_int (cfg, (int) len);
+
+       gunichar2 *u = u8to16 (str);
+       for (int i = 0; i < len; i++)
+               write_short (cfg, u[i]);
+}
+
+static void
+add_pool_entry (MonoCompile *cfg, ConstantPoolEntry *entry)
+{
+       int *cp_id= (int *) mono_mempool_alloc0 (cfg->mempool, sizeof (int));
+       *cp_id = cfg->gdump_ctx->next_cp_id;
+       g_hash_table_insert (cfg->gdump_ctx->constant_pool, entry, cp_id);
+       write_byte (cfg, POOL_NEW);
+       write_short (cfg, cfg->gdump_ctx->next_cp_id++);
+       switch (entry->pt) {
+               case PT_STRING:
+                       write_byte (cfg, POOL_STRING);
+                       write_string (cfg, (char *) entry->data);
+                       break;
+               case PT_METHOD: {
+                       MonoMethod *method = (MonoMethod *) entry->data;
+                       write_byte (cfg, POOL_METHOD);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) method->klass, PT_KLASS));
+                       write_pool (cfg, create_cp_entry (cfg, (void *) method->name, PT_STRING));
+                       write_pool (cfg, create_cp_entry (cfg, (void *) method->signature, PT_SIGNATURE));
+                       write_int (cfg, (int) method->flags);
+                       write_int (cfg, -1); // don't transmit bytecode.
+                       break;
+               }
+               case PT_KLASS: {
+                       MonoClass *klass = (MonoClass *) entry->data;
+                       write_byte (cfg, POOL_KLASS);
+                       write_string (cfg, klass->name);
+                       write_byte (cfg, KLASS);
+                       break;
+               }
+               case PT_SIGNATURE: {
+                       write_byte (cfg, POOL_SIGNATURE);
+                       MonoMethodSignature *sig = (MonoMethodSignature *) entry->data;
+                       write_short (cfg, sig->param_count);
+                       for (int i = 0; i < sig->param_count; i++) {
+                               GString *sbuf = g_string_new (NULL);
+                               mono_type_get_desc (sbuf, sig->params [i], TRUE);
+                               write_pool (cfg, create_cp_entry (cfg, (void *) sbuf->str, PT_STRING));
+                               g_string_free (sbuf, TRUE);
+                       }
+                       GString *sbuf = g_string_new (NULL);
+                       mono_type_get_desc (sbuf, sig->ret, TRUE);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) sbuf->str, PT_STRING));
+                       g_string_free (sbuf, TRUE);
+                       break;
+               }
+               case PT_OPTYPE: {
+                       MonoInst *insn = (MonoInst *) entry->data;
+                       write_byte (cfg, POOL_NODE_CLASS);
+
+                       write_string (cfg, mono_inst_name (insn->opcode));
+                       GString *insndesc = mono_print_ins_index_strbuf (-1, insn);
+                       int len = strnlen (insndesc->str, 0x2000);
+#define CUTOFF 40
+                       if (len > CUTOFF) {
+                               insndesc->str[CUTOFF] = '\0';
+                               insndesc->str[CUTOFF - 1] = '.';
+                               insndesc->str[CUTOFF - 2] = '.';
+                       }
+                       write_string (cfg, insndesc->str);
+                       if (len > CUTOFF)
+                               insndesc->str[CUTOFF] = ' ';
+                       g_string_free (insndesc, TRUE);
+
+                       // one predecessor
+                       write_short (cfg, 1);
+                       write_byte (cfg, 0);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) "predecessor", PT_STRING));
+                       write_pool (cfg, create_cp_entry (cfg, (void *) NULL, PT_INPUTTYPE));
+
+                       // make NUM_SUCCESSOR successor edges, not everyone will be used.
+#define NUM_SUCCESSOR 5
+                       write_short (cfg, NUM_SUCCESSOR);
+                       for (int i = 0; i < NUM_SUCCESSOR; i++) {
+                               char *str = g_strdup ("successor1");
+                               str[9] = '0' + i;
+                               write_byte (cfg, 0);
+                               write_pool (cfg, create_cp_entry (cfg, (void *) str, PT_STRING));
+                       }
+
+                       break;
+               }
+               case PT_INPUTTYPE: {
+                       write_byte (cfg, POOL_ENUM);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) NULL, PT_ENUMKLASS));
+                       write_int (cfg, 0);
+                       break;
+               }
+               case PT_ENUMKLASS: {
+                       write_byte (cfg, POOL_KLASS);
+                       write_string (cfg, "InputType");
+                       write_byte (cfg, ENUM_KLASS);
+                       write_int (cfg, 1);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) "fixed", PT_STRING));
+                       break;
+               }
+       }
+}
+
+static void
+write_pool (MonoCompile *cfg, ConstantPoolEntry *entry)
+{
+       if (!entry || !entry->data) {
+               write_byte (cfg, POOL_NULL);
+               return;
+       }
+
+       short *cp_index = (short *) g_hash_table_lookup (cfg->gdump_ctx->constant_pool, entry);
+       if (cp_index == NULL)
+               add_pool_entry (cfg, entry);
+       else {
+               switch (entry->pt) {
+                       case PT_STRING: write_byte (cfg, POOL_STRING); break;
+                       case PT_METHOD: write_byte (cfg, POOL_METHOD); break;
+                       case PT_ENUMKLASS: write_byte (cfg, POOL_KLASS); break;
+                       case PT_KLASS: write_byte (cfg, POOL_KLASS); break;
+                       case PT_SIGNATURE: write_byte (cfg, POOL_SIGNATURE); break;
+                       case PT_OPTYPE: write_byte (cfg, POOL_NODE_CLASS); break;
+                       case PT_INPUTTYPE: write_byte (cfg, POOL_ENUM); break;
+               }
+               write_short (cfg, *cp_index);
+       }
+}
+
+void
+mono_cfg_dump_begin_group (MonoCompile *cfg)
+{
+       if (cfg->gdump_ctx == NULL)
+               return;
+       write_byte (cfg, BEGIN_GROUP);
+       char *title = (char *) mono_mempool_alloc0 (cfg->mempool, 0x2000);
+       sprintf (title, "%s::%s", cfg->method->klass->name, cfg->method->name);
+       write_pool (cfg, create_cp_entry (cfg, (void *) title, PT_STRING));
+       write_pool (cfg, create_cp_entry (cfg, (void *) cfg->method->name, PT_STRING));
+       write_pool (cfg, create_cp_entry (cfg, (void *) cfg->method, PT_METHOD));
+       write_int (cfg, 0); // TODO: real bytecode index.
+}
+
+void
+mono_cfg_dump_close_group (MonoCompile *cfg)
+{
+       if (cfg->gdump_ctx == NULL)
+               return;
+       write_byte (cfg, CLOSE_GROUP);
+       cfg->gdump_ctx = NULL;
+}
+
+static int
+label_instructions (MonoCompile *cfg)
+{
+       MonoBasicBlock *bb;
+       int instruction_count = 0;
+
+       for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
+               cfg_debug ("bb: %d (in: %d, out: %d)", bb->block_num, bb->in_count, bb->out_count);
+               MonoInst *insn;
+               for (insn = bb->code; insn; insn = insn->next) {
+                       instruction_count++;
+                       void *id = g_hash_table_lookup (cfg->gdump_ctx->insn2id, insn);
+                       if (id != NULL) // already in the table.
+                               continue;
+                       int *new_id = (int *) mono_mempool_alloc0 (cfg->mempool, sizeof (int));
+                       *new_id = cfg->gdump_ctx->next_insn_id++;
+                       g_hash_table_insert (cfg->gdump_ctx->insn2id, insn, new_id);
+#ifdef CFG_DEBUG
+                       GString *insndesc = mono_print_ins_index_strbuf (-1, insn);
+                       cfg_debug ("> insn%002d: %s", *new_id, insndesc->str);
+                       g_string_free (insndesc, TRUE);
+#endif
+               }
+       }
+       return instruction_count;
+}
+
+static void
+write_instructions (MonoCompile *cfg, int instruction_count)
+{
+       MonoBasicBlock *bb;
+       write_int (cfg, instruction_count);
+       for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
+               MonoInst *insn;
+               cfg_debug ("== bb: %d (in: %d, out: %d) ==", bb->block_num, bb->in_count, bb->out_count);
+               for (insn = bb->code; insn; insn = insn->next) {
+                       int i;
+                       int *id = (int *) g_hash_table_lookup (cfg->gdump_ctx->insn2id, insn);
+                       g_assert (id);
+                       write_int (cfg, *id);
+
+                       // hardcoded node class: only one input and NUM_SUCCESSOR successors
+                       write_pool (cfg, create_cp_entry (cfg, (void *) insn, PT_OPTYPE));
+                       write_byte (cfg, cfg->bb_entry->code != insn);
+
+                       // properties
+                       write_short (cfg, 2);
+
+                       // property #1
+                       GString *insndesc = mono_print_ins_index_strbuf (-1, insn);
+                       cfg_debug ("dumping node [%2d]: %s", *id, insndesc->str);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) "fullname", PT_STRING));
+                       write_byte (cfg, PROPERTY_POOL);
+                       write_pool (cfg, create_cp_entry (cfg, (void *) insndesc->str, PT_STRING));
+                       g_string_free (insndesc, TRUE);
+
+                       // property #2
+                       write_pool (cfg, create_cp_entry (cfg, (void *) "category", PT_STRING));
+                       write_byte (cfg, PROPERTY_POOL);
+                       if (bb->in_count > 1 && bb->code == insn)
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "merge", PT_STRING));
+                       else if (bb->code == insn)
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "begin", PT_STRING));
+                       else if (MONO_IS_COND_BRANCH_OP (insn))
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "controlSplit", PT_STRING));
+                       else if (MONO_IS_PHI (insn))
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "phi", PT_STRING));
+                       else if (!MONO_INS_HAS_NO_SIDE_EFFECT (insn))
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "state", PT_STRING));
+                       else
+                               write_pool (cfg, create_cp_entry (cfg, (void *) "fixed", PT_STRING));
+                       // end of properties
+                       write_int (cfg, -1); // never set predecessor.
+
+                       int *next_id;
+                       if (insn->next != NULL) {
+                               next_id = (int *) g_hash_table_lookup (cfg->gdump_ctx->insn2id, insn->next);
+                               g_assert (next_id);
+                               cfg_debug ("\tsuccessor' : [%2d]", *next_id);
+                               write_int (cfg, *next_id);
+                               for (i = 1; i < NUM_SUCCESSOR; i++)
+                                       write_int (cfg, -1);
+                       } else {
+                               g_assert (bb->out_count < NUM_SUCCESSOR);
+                               for (i = 0; (i < bb->out_count) && (i < NUM_SUCCESSOR); i++) {
+                                       if (bb->out_bb[i]->code == NULL)
+                                               write_int (cfg, -1);
+                                       else {
+                                               next_id = (int *) g_hash_table_lookup (cfg->gdump_ctx->insn2id, bb->out_bb[i]->code);
+                                               if (next_id)
+                                                       cfg_debug ("\tsuccessor'': [%2d]", *next_id);
+                                               write_int (cfg, next_id ? *next_id : -1);
+                                       }
+                               }
+                               for (; i < NUM_SUCCESSOR; i++)
+                                       write_int (cfg, -1);
+                       }
+               }
+       }
+}
+
+static void
+write_blocks (MonoCompile *cfg)
+{
+       int block_size = 0;
+       MonoBasicBlock *bb;
+       for (bb = cfg->bb_entry; bb; bb = bb->next_bb)
+               block_size++;
+       write_int (cfg, block_size);
+
+       for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
+               int insn_size = 0;
+               MonoInst *insn = NULL;
+
+               write_int (cfg, bb->block_num);
+
+               for (insn = bb->code; insn; insn = insn->next)
+                       insn_size++;
+               write_int (cfg, insn_size);
+
+               for (insn = bb->code; insn; insn = insn->next) {
+                       int *id = (int *) g_hash_table_lookup (cfg->gdump_ctx->insn2id, insn);
+                       g_assert (id);
+                       write_int (cfg, *id);
+               }
+
+               write_int (cfg, bb->out_count);
+               for (int i = 0; i < bb->out_count; i++)
+                       write_int (cfg, bb->out_bb[i]->block_num);
+       }
+}
+
+static guint
+instruction_hash (MonoInst *insn)
+{
+       guint res = 0;
+       res  = insn->opcode << 0x00;
+       res ^= insn->type   << 0x04;
+       res ^= insn->flags  << 0x08;
+       res ^= insn->dreg   << 0x0c;
+       res ^= insn->sreg1  << 0x10;
+       res ^= insn->sreg2  << 0x14;
+       res ^= insn->sreg3  << 0x18;
+       res ^= (guint) insn->next;
+       res ^= (guint) insn->prev;
+       res ^= (guint) insn;
+       return res;
+}
+
+static gboolean
+instruction_equal (gconstpointer v1, gconstpointer v2)
+{
+       MonoInst *i1 = (MonoInst *) v1;
+       MonoInst *i2 = (MonoInst *) v2;
+
+       if (i1->opcode != i2->opcode || i1->type != i2->type || i1->flags != i2->flags)
+               return FALSE;
+       if (i1->dreg != i2->dreg || i1->sreg1 != i2->sreg1 || i1->sreg2 != i2->sreg2 || i1->sreg3 != i2->sreg3)
+               return FALSE;
+       if (i1->next != i2->next || i1->prev != i2->prev)
+               return FALSE;
+       return TRUE;
+}
+
+static guint
+constant_pool_hash (ConstantPoolEntry *entry)
+{
+       switch (entry->pt) {
+               case PT_STRING:
+                       return g_str_hash (entry->data);
+               case PT_METHOD: {
+                       MonoMethod *method = (MonoMethod *) entry->data;
+                       return g_str_hash (method->name) ^ g_str_hash (method->klass);
+               }
+               case PT_KLASS:
+                       return g_str_hash (((MonoClass *) entry->data)->name);
+               case PT_OPTYPE:
+                       return instruction_hash ((MonoInst *) entry->data);
+               case PT_SIGNATURE: {
+                       MonoMethodSignature *sig = (MonoMethodSignature *) entry->data;
+                       guint ret = (guint) sig->ret;
+                       for (int i = 0; i < sig->param_count; i++) {
+                               ret ^= (guint) sig->params [i] << (i + 1);
+                       }
+                       return ret;
+               }
+               case PT_INPUTTYPE: // TODO: singleton.
+               case PT_ENUMKLASS:
+                       return (guint) entry->data;
+       }
+       g_assert (FALSE);
+       return FALSE;
+}
+
+static gboolean
+constant_pool_equal (gconstpointer v1, gconstpointer v2)
+{
+       ConstantPoolEntry *e1 = (ConstantPoolEntry *) v1;
+       ConstantPoolEntry *e2 = (ConstantPoolEntry *) v2;
+       if (e1->pt != e2->pt)
+               return FALSE;
+
+       switch (e1->pt) {
+               case PT_STRING:
+                       return g_str_equal (e1->data, e2->data);
+               case PT_OPTYPE:
+                       return instruction_equal (e1->data, e2->data);
+               case PT_METHOD: // TODO: implement proper equal.
+               case PT_KLASS:
+               case PT_SIGNATURE:
+                       return constant_pool_hash (e1) == constant_pool_hash (e2);
+               case PT_INPUTTYPE: // TODO: singleton.
+               case PT_ENUMKLASS:
+                       return TRUE;
+       }
+       g_assert (FALSE);
+       return FALSE;
+}
+
+
+static gboolean cfg_dump_method_inited = FALSE;
+static const char *cfg_dump_method_name;
+
+void mono_cfg_dump_create_context (MonoCompile *cfg)
+{
+       cfg->gdump_ctx = NULL;
+
+       if (!cfg_dump_method_inited) {
+               cfg_dump_method_name = g_getenv ("MONO_JIT_DUMP_METHOD");
+               cfg_dump_method_inited = TRUE;
+       }
+       if (!cfg_dump_method_name)
+               return;
+       const char *name = cfg_dump_method_name;
+
+       if ((strchr (name, '.') > name) || strchr (name, ':')) {
+               MonoMethodDesc *desc = mono_method_desc_new (name, TRUE);
+               gboolean failed = !mono_method_desc_full_match (desc, cfg->method);
+               mono_method_desc_free (desc);
+               if (failed)
+                       return;
+       } else
+               if (strcmp (cfg->method->name, name) != 0)
+                       return;
+
+       g_debug ("cfg_dump: create context for \"%s::%s\"", cfg->method->klass->name, cfg->method->name);
+       int fd = create_socket (DEFAULT_HOST, DEFAULT_PORT);
+       if (fd < 0) {
+               g_warning ("cfg_dump: couldn't create socket: %s::%d", DEFAULT_HOST, DEFAULT_PORT);
+               return;
+       }
+
+       MonoGraphDumper *ctx = (MonoGraphDumper *) mono_mempool_alloc0 (cfg->mempool, sizeof (MonoGraphDumper));
+       ctx->fd = fd;
+       ctx->constant_pool = g_hash_table_new ((GHashFunc) constant_pool_hash, constant_pool_equal);
+       ctx->insn2id = g_hash_table_new ((GHashFunc) instruction_hash, instruction_equal);
+       ctx->next_cp_id = 1;
+       ctx->next_insn_id = 0;
+
+       cfg->gdump_ctx = ctx;
+}
+
+void
+mono_cfg_dump_ir (MonoCompile *cfg, const char *phase_name)
+{
+       if (cfg->gdump_ctx == NULL)
+               return;
+       cfg_debug ("=== DUMPING PASS \"%s\" ===", phase_name);
+       write_byte (cfg, BEGIN_GRAPH);
+       write_pool (cfg, create_cp_entry (cfg, (void *) phase_name, PT_STRING));
+
+       int instruction_count = label_instructions (cfg);
+       write_instructions (cfg, instruction_count);
+       write_blocks (cfg);
+}
+#else /* !defined(DISABLE_LOGGING) && !defined(DISABLE_JIT) && !defined(HOST_WIN32) */
+void
+mono_cfg_dump_create_context (MonoCompile *cfg)
+{
+}
+
+void
+mono_cfg_dump_begin_group (MonoCompile *cfg)
+{
+}
+
+void
+mono_cfg_dump_close_group (MonoCompile *cfg)
+{
+}
+
+void
+mono_cfg_dump_ir (MonoCompile *cfg, const char *phase_name)
+{
+}
+#endif /* !defined(DISABLE_LOGGING) && !defined(DISABLE_JIT) && !defined(HOST_WIN32) */
diff --git a/mono/mini/cfgdump.h b/mono/mini/cfgdump.h
new file mode 100644 (file)
index 0000000..ef58553
--- /dev/null
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2016 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+#ifndef __MINI_CFGDUMP_H__
+#define __MINI_CFGDUMP_H__
+#include <glib.h>
+
+#define CONSTANT_POOL_MAX_SIZE 8000
+
+#define BEGIN_GROUP 0x00
+#define BEGIN_GRAPH 0x01
+#define CLOSE_GROUP 0x02
+
+#define POOL_NEW 0x00
+#define POOL_STRING 0x01
+#define POOL_ENUM 0x02
+#define POOL_KLASS 0x03
+#define POOL_METHOD 0x04
+#define POOL_NULL 0x05
+#define POOL_NODE_CLASS 0x06
+#define POOL_FIELD 0x07
+#define POOL_SIGNATURE 0x08
+
+#define PROPERTY_POOL 0x00
+#define PROPERTY_INT 0x01
+#define PROPERTY_LONG 0x02
+#define PROPERTY_DOUBLE 0x03
+#define PROPERTY_FLOAT 0x04
+#define PROPERTY_TRUE 0x05
+#define PROPERTY_FALSE 0x06
+#define PROPERTY_ARRAY 0x07
+#define PROPERTY_SUBGRAPH 0x08
+
+#define KLASS 0x00
+#define ENUM_KLASS 0x01
+
+
+#define DEFAULT_PORT 4445
+#define DEFAULT_HOST "127.0.0.1"
+
+typedef enum {
+       PT_STRING,
+       PT_METHOD,
+       PT_KLASS,
+       PT_OPTYPE,
+       PT_INPUTTYPE,
+       PT_ENUMKLASS,
+       PT_SIGNATURE
+} pool_type;
+
+struct _MonoGraphDumper {
+       int fd;
+       GHashTable *constant_pool;
+       short next_cp_id;
+       GHashTable *insn2id;
+       int next_insn_id;
+};
+
+typedef struct _MonoGraphDumper MonoGraphDumper;
+
+struct _ConstantPoolEntry {
+       pool_type pt;
+       void *data;
+};
+
+typedef struct _ConstantPoolEntry ConstantPoolEntry;
+#endif /* __MINI_CFGDUMP_H__ */
index cd51ad72c94a6965fee19bda4aaad8c0cedc9951..24694376aacce167ba9e25b15709d8863268d232 100644 (file)
@@ -1,5 +1,6 @@
 # Copyright 2003-2011 Novell, Inc (http://www.novell.com)
 # Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+# Licensed under the MIT license. See LICENSE file in the project root for full license information.
 # arm cpu description file
 # this file is read by genmdesc to pruduce a table with all the relevant information
 # about the cpu instructions that may be used by the regsiter allocator, the scheduler
index 440e6a69e14b46711625758d458e12955ddc9f5a..a8eea0965d54bb34f9263672de5063974c378e48 100644 (file)
@@ -1,5 +1,6 @@
 # Copyright 2011-2013 Xamarin, Inc (http://www.xamarin.com)
 # Copyright 2003-2011 Novell, Inc (http://www.novell.com)
+# Licensed under the MIT license. See LICENSE file in the project root for full license information.
 # arm64 cpu description file
 # this file is read by genmdesc to pruduce a table with all the relevant information
 # about the cpu instructions that may be used by the regsiter allocator, the scheduler
index e9bdc72ad4607f2a3cb80ece48c7bdbb583e0d7e..8c4d16aa4f27b4a3fb88d33e64e4e858d048365e 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2009-2010 Novell, Inc.
  * Copyright 2011 Xamarin Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -6031,6 +6032,7 @@ decode_value_internal (MonoType *t, int type, MonoDomain *domain, guint8 *addr,
                        } else if (type == VALUE_TYPE_ID_NULL) {
                                *(MonoObject**)addr = NULL;
                        } else if (type == MONO_TYPE_VALUETYPE) {
+                               MonoError error;
                                guint8 *buf2;
                                gboolean is_enum;
                                MonoClass *klass;
@@ -6062,7 +6064,8 @@ decode_value_internal (MonoType *t, int type, MonoDomain *domain, guint8 *addr,
                                        g_free (vtype_buf);
                                        return err;
                                }
-                               *(MonoObject**)addr = mono_value_box (d, klass, vtype_buf);
+                               *(MonoObject**)addr = mono_value_box_checked (d, klass, vtype_buf, &error);
+                               mono_error_cleanup (&error);
                                g_free (vtype_buf);
                        } else {
                                char *name = mono_type_full_name (t);
@@ -6084,6 +6087,7 @@ decode_value_internal (MonoType *t, int type, MonoDomain *domain, guint8 *addr,
 static ErrorCode
 decode_value (MonoType *t, MonoDomain *domain, guint8 *addr, guint8 *buf, guint8 **endbuf, guint8 *limit)
 {
+       MonoError error;
        ErrorCode err;
        int type = decode_byte (buf, &buf, limit);
 
@@ -6108,7 +6112,12 @@ decode_value (MonoType *t, MonoDomain *domain, guint8 *addr, guint8 *buf, guint8
                                g_free (nullable_buf);
                                return err;
                        }
-                       mono_nullable_init (addr, mono_value_box (domain, mono_class_from_mono_type (targ), nullable_buf), mono_class_from_mono_type (t));
+                       MonoObject *boxed = mono_value_box_checked (domain, mono_class_from_mono_type (targ), nullable_buf, &error);
+                       if (!is_ok (&error)) {
+                               mono_error_cleanup (&error);
+                               return ERR_INVALID_OBJECT;
+                       }
+                       mono_nullable_init (addr, boxed, mono_class_from_mono_type (t));
                        g_free (nullable_buf);
                        *endbuf = buf;
                        return ERR_NONE;
@@ -7249,7 +7258,7 @@ vm_commands (int command, int id, guint8 *p, guint8 *end, Buffer *buf)
                                        MonoError error;
                                        type_resolve = TRUE;
                                        /* FIXME really okay to call while holding locks? */
-                                       t = mono_reflection_get_type_checked (ass->image, &info, ignore_case, &type_resolve, &error);
+                                       t = mono_reflection_get_type_checked (ass->image, ass->image, &info, ignore_case, &type_resolve, &error);
                                        mono_error_cleanup (&error); 
                                        if (t) {
                                                g_ptr_array_add (res_classes, mono_type_get_class (t));
@@ -7683,7 +7692,7 @@ assembly_commands (int command, guint8 *p, guint8 *end, Buffer *buf)
                } else {
                        if (info.assembly.name)
                                NOT_IMPLEMENTED;
-                       t = mono_reflection_get_type_checked (ass->image, &info, ignorecase, &type_resolve, &error);
+                       t = mono_reflection_get_type_checked (ass->image, ass->image, &info, ignorecase, &type_resolve, &error);
                        if (!is_ok (&error)) {
                                mono_error_cleanup (&error); /* FIXME don't swallow the error */
                                mono_reflection_free_type_info (&info);
@@ -9246,6 +9255,7 @@ string_commands (int command, guint8 *p, guint8 *end, Buffer *buf)
 static ErrorCode
 object_commands (int command, guint8 *p, guint8 *end, Buffer *buf)
 {
+       MonoError error;
        int objid;
        ErrorCode err;
        MonoObject *obj;
@@ -9323,7 +9333,11 @@ object_commands (int command, guint8 *p, guint8 *end, Buffer *buf)
 
                                if (remote_obj) {
 #ifndef DISABLE_REMOTING
-                                       field_value = mono_load_remote_field(obj, obj_type, f, &field_storage);
+                                       field_value = mono_load_remote_field_checked(obj, obj_type, f, &field_storage, &error);
+                                       if (!is_ok (&error)) {
+                                               mono_error_cleanup (&error); /* FIXME report the error */
+                                               return ERR_INVALID_OBJECT;
+                                       }
 #else
                                        g_assert_not_reached ();
 #endif
@@ -9666,6 +9680,7 @@ wait_for_attach (void)
 static guint32 WINAPI
 debugger_thread (void *arg)
 {
+       MonoError error;
        int res, len, id, flags, command = 0;
        CommandSet command_set = (CommandSet)0;
        guint8 header [HEADER_LENGTH];
@@ -9681,8 +9696,11 @@ debugger_thread (void *arg)
        debugger_thread_id = mono_native_thread_id_get ();
 
        attach_cookie = mono_jit_thread_attach (mono_get_root_domain (), &attach_dummy);
+       MonoInternalThread *thread = mono_thread_internal_current ();
+       mono_thread_set_name_internal (thread, mono_string_new (mono_get_root_domain (), "Debugger agent"), TRUE, &error);
+       mono_error_assert_ok (&error);
 
-       mono_thread_internal_current ()->flags |= MONO_THREAD_FLAG_DONT_MANAGE;
+       thread->flags |= MONO_THREAD_FLAG_DONT_MANAGE;
 
        mono_set_is_debugger_attached (TRUE);
        
index 10c8c75e134d359dd829d023521131246a1f8f67..45849a824337eb2fd5dd7bb8d9eae312640afd27 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mini.h"
@@ -932,6 +933,8 @@ mono_decompose_long_opts (MonoCompile *cfg)
                                MONO_EMIT_NEW_BIALU_IMM (cfg, OP_XOR_IMM, MONO_LVREG_LS (tree->dreg), MONO_LVREG_LS (tree->sreg1), tree->inst_ls_word);
                                MONO_EMIT_NEW_BIALU_IMM (cfg, OP_XOR_IMM, MONO_LVREG_MS (tree->dreg), MONO_LVREG_MS (tree->sreg1), tree->inst_ms_word);
                                break;
+#ifdef TARGET_POWERPC
+/* FIXME This is normally handled in cprop. Proper fix or remove if no longer needed. */
                        case OP_LSHR_UN_IMM:
                                if (tree->inst_c1 == 32) {
 
@@ -940,20 +943,12 @@ mono_decompose_long_opts (MonoCompile *cfg)
                                         * later apply the speedup to the left shift as well
                                         * See BUG# 57957.
                                         */
-                                       /* FIXME: Move this to the strength reduction pass */
                                        /* just move the upper half to the lower and zero the high word */
                                        MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (tree->dreg), MONO_LVREG_MS (tree->sreg1));
                                        MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_MS (tree->dreg), 0);
                                }
                                break;
-                       case OP_LSHL_IMM:
-                               if (tree->inst_c1 == 32) {
-                                       /* just move the lower half to the upper and zero the lower word */
-                                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_MS (tree->dreg), MONO_LVREG_LS (tree->sreg1));
-                                       MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_LS (tree->dreg), 0);
-                               }
-                               break;
-
+#endif
                        case OP_LCOMPARE: {
                                MonoInst *next = mono_inst_next (tree, FILTER_IL_SEQ_POINT);
 
@@ -1525,7 +1520,7 @@ mono_decompose_array_access_opts (MonoCompile *cfg)
                                                MONO_INST_NEW (cfg, iargs [2], OP_MOVE);
                                                iargs [2]->dreg = ins->sreg1;
 
-                                               dest = mono_emit_jit_icall (cfg, mono_array_new, iargs);
+                                               dest = mono_emit_jit_icall (cfg, ves_icall_array_new, iargs);
                                                dest->dreg = ins->dreg;
                                        } else {
                                                MonoClass *array_class = mono_array_class_get (ins->inst_newa_class, 1);
index ab3ba6333cce8f5c11d47acd8c0b7759ce421275..b4c8dc39056147e947786a6c25efdbeb80096296 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2003 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <string.h>
 #include <mono/metadata/debug-helpers.h>
index 5b717fcd5e04dbd5f0ac006d916de79bdb802e9a..a955b44643373c24d61f2f2bb63f9fd2a49e1529 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2002-2003 Ximian, Inc.
  * (C) 2003-2006 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -850,6 +851,7 @@ small_id_thread_func (gpointer arg)
 static void
 jit_info_table_test (MonoDomain *domain)
 {
+       MonoError error;
        int i;
 
        g_print ("testing jit_info_table\n");
@@ -878,8 +880,10 @@ jit_info_table_test (MonoDomain *domain)
        sleep (2);
        */
 
-       for (i = 0; i < num_threads; ++i)
-               mono_thread_create (domain, test_thread_func, &thread_datas [i]);
+       for (i = 0; i < num_threads; ++i) {
+               mono_thread_create_checked (domain, test_thread_func, &thread_datas [i], &error);
+               mono_error_assert_ok (&error);
+       }
 }
 #endif
 
@@ -972,6 +976,7 @@ compile_all_methods_thread_main (CompileAllThreadArgs *args)
 static void
 compile_all_methods (MonoAssembly *ass, int verbose, guint32 opts, guint32 recompilation_times)
 {
+       MonoError error;
        CompileAllThreadArgs args;
 
        args.ass = ass;
@@ -983,7 +988,8 @@ compile_all_methods (MonoAssembly *ass, int verbose, guint32 opts, guint32 recom
         * Need to create a mono thread since compilation might trigger
         * running of managed code.
         */
-       mono_thread_create (mono_domain_get (), compile_all_methods_thread_main, &args);
+       mono_thread_create_checked (mono_domain_get (), compile_all_methods_thread_main, &args, &error);
+       mono_error_assert_ok (&error);
 
        mono_thread_manage ();
 }
@@ -1139,7 +1145,7 @@ load_agent (MonoDomain *domain, char *desc)
 
        method = mono_get_method_checked (image, entry, NULL, NULL, &error);
        if (method == NULL){
-               g_print ("The entry point method of assembly '%s' could not be loaded due to %s\n", agent, &error);
+               g_print ("The entry point method of assembly '%s' could not be loaded due to %s\n", agent, mono_error_get_message (&error));
                mono_error_cleanup (&error);
                g_free (agent);
                return 1;
@@ -1148,12 +1154,19 @@ load_agent (MonoDomain *domain, char *desc)
        mono_thread_set_main (mono_thread_current ());
 
        if (args) {
-               main_args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, 1);
-               mono_array_set (main_args, MonoString*, 0, mono_string_new (domain, args));
+               main_args = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, 1, &error);
+               if (main_args)
+                       mono_array_set (main_args, MonoString*, 0, mono_string_new (domain, args));
        } else {
-               main_args = (MonoArray*)mono_array_new (domain, mono_defaults.string_class, 0);
+               main_args = (MonoArray*)mono_array_new_checked (domain, mono_defaults.string_class, 0, &error);
        }
-
+       if (!main_args) {
+               g_print ("Could not allocate array for main args of assembly '%s' due to %s\n", agent, mono_error_get_message (&error));
+               mono_error_cleanup (&error);
+               g_free (agent);
+               return 1;
+       }
+       
        g_free (agent);
 
        pa [0] = main_args;
@@ -1190,6 +1203,8 @@ mini_usage_jitdeveloper (void)
                 "    --agent=ASSEMBLY[:ARG] Loads the specific agent assembly and executes its Main method with the given argument before loading the main assembly.\n"
                 "    --no-x86-stack-align   Don't align stack on x86\n"
                 "\n"
+                "The options supported by MONO_DEBUG can also be passed on the command line.\n"
+                "\n"
                 "Other options:\n" 
                 "    --graph[=TYPE] METHOD  Draws a graph of the specified method:\n");
        
@@ -1439,6 +1454,7 @@ mono_jit_parse_options (int argc, char * argv[])
 #else
                        mono_use_llvm = TRUE;
 #endif
+               } else if (argv [i][0] == '-' && argv [i][1] == '-' && mini_parse_debug_option (argv [i] + 2)) {
                } else {
                        fprintf (stderr, "Unsupported command line option: '%s'\n", argv [i]);
                        exit (1);
@@ -1633,19 +1649,6 @@ mono_main (int argc, char* argv[])
                        gc_descr = mono_gc_get_description ();
                        g_print ("\tGC:            %s\n", gc_descr);
                        g_free (gc_descr);
-                       if (mini_verbose) {
-                               const char *cerror;
-                               const char *clibpath;
-                               mono_init ("mono");
-                               cerror = mono_check_corlib_version ();
-                               clibpath = mono_defaults.corlib? mono_image_get_filename (mono_defaults.corlib): "unknown";
-                               if (cerror) {
-                                       g_print ("The currently installed mscorlib doesn't match this runtime version.\n");
-                                       g_print ("The error is: %s\n", cerror);
-                                       g_print ("mscorlib.dll loaded at: %s\n", clibpath);
-                                       return 1;
-                               }
-                       }
                        return 0;
                } else if (strcmp (argv [i], "--help") == 0 || strcmp (argv [i], "-h") == 0) {
                        mini_usage ();
@@ -1911,6 +1914,7 @@ mono_main (int argc, char* argv[])
                } else if (strcmp (argv [i], "--nacl-null-checks-off") == 0){
                        nacl_null_checks_off = TRUE;
 #endif
+               } else if (argv [i][0] == '-' && argv [i][1] == '-' && mini_parse_debug_option (argv [i] + 2)) {
                } else {
                        fprintf (stderr, "Unknown command line option: '%s'\n", argv [i]);
                        return 1;
@@ -1982,8 +1986,16 @@ mono_main (int argc, char* argv[])
        /* Set rootdir before loading config */
        mono_set_rootdir ();
 
-       if (enable_profile)
+       /*
+        * We only set the native name of the thread since MS.NET leaves the
+        * managed thread name for the main thread as null.
+        */
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Main");
+
+       if (enable_profile) {
                mono_profiler_load (profile_options);
+               mono_profiler_thread_name (MONO_NATIVE_THREAD_ID_TO_UINT (mono_native_thread_id_get ()), "Main");
+       }
 
        mono_attach_parse_options (attach_options);
 
@@ -2364,83 +2376,154 @@ mono_set_crash_chaining (gboolean chain_crashes)
        mono_do_crash_chaining = chain_crashes;
 }
 
-void
-mono_parse_env_options (int *ref_argc, char **ref_argv [])
+/**
+ * mono_parse_options_from:
+ * @options: string containing strings 
+ * @ref_argc: pointer to the argc variable that might be updated 
+ * @ref_argv: pointer to the argv string vector variable that might be updated
+ *
+ * This function parses the contents of the `MONO_ENV_OPTIONS`
+ * environment variable as if they were parsed by a command shell
+ * splitting the contents by spaces into different elements of the
+ * @argv vector.  This method supports quoting with both the " and '
+ * characters.  Inside quoting, spaces and tabs are significant,
+ * otherwise, they are considered argument separators.
+ *
+ * The \ character can be used to escape the next character which will
+ * be added to the current element verbatim.  Typically this is used
+ * inside quotes.   If the quotes are not balanced, this method 
+ *
+ * If the environment variable is empty, no changes are made
+ * to the values pointed by @ref_argc and @ref_argv.
+ *
+ * Otherwise the @ref_argv is modified to point to a new array that contains
+ * all the previous elements contained in the vector, plus the values parsed.
+ * The @argc is updated to match the new number of parameters.
+ *
+ * Returns: The value NULL is returned on success, otherwise a g_strdup allocated
+ * string is returned (this is an alias to malloc under normal circumstances) that
+ * contains the error message that happened during parsing.
+ */
+char *
+mono_parse_options_from (const char *options, int *ref_argc, char **ref_argv [])
 {
        int argc = *ref_argc;
        char **argv = *ref_argv;
-
-       const char *env_options = g_getenv ("MONO_ENV_OPTIONS");
-       if (env_options != NULL){
-               GPtrArray *array = g_ptr_array_new ();
-               GString *buffer = g_string_new ("");
-               const char *p;
-               unsigned i;
-               gboolean in_quotes = FALSE;
-               char quote_char = '\0';
-
-               for (p = env_options; *p; p++){
-                       switch (*p){
-                       case ' ': case '\t':
-                               if (!in_quotes) {
-                                       if (buffer->len != 0){
-                                               g_ptr_array_add (array, g_strdup (buffer->str));
-                                               g_string_truncate (buffer, 0);
-                                       }
-                               } else {
-                                       g_string_append_c (buffer, *p);
-                               }
-                               break;
-                       case '\\':
-                               if (p [1]){
-                                       g_string_append_c (buffer, p [1]);
-                                       p++;
-                               }
-                               break;
-                       case '\'':
-                       case '"':
-                               if (in_quotes) {
-                                       if (quote_char == *p)
-                                               in_quotes = FALSE;
-                                       else
-                                               g_string_append_c (buffer, *p);
-                               } else {
-                                       in_quotes = TRUE;
-                                       quote_char = *p;
+       GPtrArray *array = g_ptr_array_new ();
+       GString *buffer = g_string_new ("");
+       const char *p;
+       unsigned i;
+       gboolean in_quotes = FALSE;
+       char quote_char = '\0';
+
+       if (options == NULL)
+               return NULL;
+       
+       for (p = options; *p; p++){
+               switch (*p){
+               case ' ': case '\t':
+                       if (!in_quotes) {
+                               if (buffer->len != 0){
+                                       g_ptr_array_add (array, g_strdup (buffer->str));
+                                       g_string_truncate (buffer, 0);
                                }
-                               break;
-                       default:
+                       } else {
                                g_string_append_c (buffer, *p);
-                               break;
                        }
+                       break;
+               case '\\':
+                       if (p [1]){
+                               g_string_append_c (buffer, p [1]);
+                               p++;
+                       }
+                       break;
+               case '\'':
+               case '"':
+                       if (in_quotes) {
+                               if (quote_char == *p)
+                                       in_quotes = FALSE;
+                               else
+                                       g_string_append_c (buffer, *p);
+                       } else {
+                               in_quotes = TRUE;
+                               quote_char = *p;
+                       }
+                       break;
+               default:
+                       g_string_append_c (buffer, *p);
+                       break;
                }
-               if (in_quotes) {
-                       fprintf (stderr, "Unmatched quotes in value of MONO_ENV_OPTIONS: [%s]\n", env_options);
-                       exit (1);
-               }
-                       
-               if (buffer->len != 0)
-                       g_ptr_array_add (array, g_strdup (buffer->str));
-               g_string_free (buffer, TRUE);
+       }
+       if (in_quotes) 
+               return g_strdup_printf ("Unmatched quotes in value: [%s]\n", options);
+               
+       if (buffer->len != 0)
+               g_ptr_array_add (array, g_strdup (buffer->str));
+       g_string_free (buffer, TRUE);
 
-               if (array->len > 0){
-                       int new_argc = array->len + argc;
-                       char **new_argv = g_new (char *, new_argc + 1);
-                       int j;
+       if (array->len > 0){
+               int new_argc = array->len + argc;
+               char **new_argv = g_new (char *, new_argc + 1);
+               int j;
 
-                       new_argv [0] = argv [0];
-                       
-                       /* First the environment variable settings, to allow the command line options to override */
-                       for (i = 0; i < array->len; i++)
-                               new_argv [i+1] = (char *)g_ptr_array_index (array, i);
-                       i++;
-                       for (j = 1; j < argc; j++)
-                               new_argv [i++] = argv [j];
-                       new_argv [i] = NULL;
-
-                       *ref_argc = new_argc;
-                       *ref_argv = new_argv;
-               }
-               g_ptr_array_free (array, TRUE);
+               new_argv [0] = argv [0];
+               
+               /* First the environment variable settings, to allow the command line options to override */
+               for (i = 0; i < array->len; i++)
+                       new_argv [i+1] = (char *)g_ptr_array_index (array, i);
+               i++;
+               for (j = 1; j < argc; j++)
+                       new_argv [i++] = argv [j];
+               new_argv [i] = NULL;
+
+               *ref_argc = new_argc;
+               *ref_argv = new_argv;
        }
+       g_ptr_array_free (array, TRUE);
+       return NULL;
 }
+
+/**
+ * mono_parse_env_options:
+ * @ref_argc: pointer to the argc variable that might be updated 
+ * @ref_argv: pointer to the argv string vector variable that might be updated
+ *
+ * This function parses the contents of the `MONO_ENV_OPTIONS`
+ * environment variable as if they were parsed by a command shell
+ * splitting the contents by spaces into different elements of the
+ * @argv vector.  This method supports quoting with both the " and '
+ * characters.  Inside quoting, spaces and tabs are significant,
+ * otherwise, they are considered argument separators.
+ *
+ * The \ character can be used to escape the next character which will
+ * be added to the current element verbatim.  Typically this is used
+ * inside quotes.   If the quotes are not balanced, this method 
+ *
+ * If the environment variable is empty, no changes are made
+ * to the values pointed by @ref_argc and @ref_argv.
+ *
+ * Otherwise the @ref_argv is modified to point to a new array that contains
+ * all the previous elements contained in the vector, plus the values parsed.
+ * The @argc is updated to match the new number of parameters.
+ *
+ * If there is an error parsing, this method will terminate the process by
+ * calling exit(1).
+ *
+ * An alternative to this method that allows an arbitrary string to be parsed
+ * and does not exit on error is the `api:mono_parse_options_from`.
+ */
+void
+mono_parse_env_options (int *ref_argc, char **ref_argv [])
+{
+       char *ret;
+       
+       const char *env_options = g_getenv ("MONO_ENV_OPTIONS");
+       if (env_options == NULL)
+               return;
+       ret = mono_parse_options_from (env_options, ref_argc, ref_argv);
+       if (ret == NULL)
+               return;
+       fprintf (stderr, "%s", ret);
+       exit (1);
+}
+
index 596509e6b7495cfad5f1b063fca51f95784eb50a..ad25f58728ec9c6a3de38dd253f4e0cecdb92c78 100644 (file)
@@ -53,7 +53,7 @@ struct _MonoDwarfWriter
        GSList *cie_program;
        FILE *fp;
        const char *temp_prefix;
-       gboolean emit_line, appending, collect_line_info;
+       gboolean emit_line;
        GSList *line_info;
        int cur_file_index;
 };
@@ -70,48 +70,17 @@ emit_line_number_info (MonoDwarfWriter *w, MonoMethod *method,
  *   Create a DWARF writer object. WRITER is the underlying image writer this 
  * writer will emit to. IL_FILE is the file where IL code will be dumped to for
  * methods which have no line number info. It can be NULL.
- * If APPENDING is TRUE, the output file will be in assembleable state after each
- * call to the _emit_ functions. This is used for XDEBUG. If APPENDING is FALSE,
- * a separate mono_dwarf_writer_close () call is needed to finish the emission of
- * debug information.
  */
 MonoDwarfWriter*
-mono_dwarf_writer_create (MonoImageWriter *writer, FILE *il_file, int il_file_start_line, gboolean appending, gboolean emit_line_numbers)
+mono_dwarf_writer_create (MonoImageWriter *writer, FILE *il_file, int il_file_start_line, gboolean emit_line_numbers)
 {
        MonoDwarfWriter *w = g_new0 (MonoDwarfWriter, 1);
-       
-       /*
-        * The appending flag is needed because we use subsections to order things in 
-        * the debug info, and:
-        * - apple's assembler doesn't support them
-        * - the binary writer has problems with subsections+alignment
-        * So instead of subsections, we use the _close () function in AOT mode,
-        * which writes out things in order.
-        */
 
        w->w = writer;
        w->il_file = il_file;
        w->il_file_line_index = il_file_start_line;
-       w->appending = appending;
-
-       if (appending)
-               g_assert (mono_img_writer_subsections_supported (w->w));
-
-       w->emit_line = TRUE;
-
-       if (appending) {
-               if (!mono_img_writer_subsections_supported (w->w))
-                       /* Can't emit line number info without subsections */
-                       w->emit_line = FALSE;
-       } else {
-               /* Collect line number info and emit it at once */
-               w->collect_line_info = TRUE;
-       }
 
-       if (!emit_line_numbers) {
-               w->emit_line = FALSE;
-               w->collect_line_info = FALSE;
-       }
+       w->emit_line = emit_line_numbers;
 
        w->fp = mono_img_writer_get_fp (w->w);
        w->temp_prefix = mono_img_writer_get_temp_label_prefix (w->w);
@@ -603,71 +572,6 @@ static DwarfBasicType basic_types [] = {
 #define LINE_BASE -5
 #define LINE_RANGE 14
 
-/* Subsections of the .debug_line section */
-#define LINE_SUBSECTION_HEADER 1
-#define LINE_SUBSECTION_INCLUDES 2
-#define LINE_SUBSECTION_FILES 3
-#define LINE_SUBSECTION_DATA 4
-#define LINE_SUBSECTION_END 5
-
-static int
-emit_line_number_file_name (MonoDwarfWriter *w, const char *name,
-                                                       gint64 last_mod_time, gint64 file_size)
-{
-       int index;
-       int dir_index;
-       char *basename = NULL;
-
-       if (!w->file_to_index)
-               w->file_to_index = g_hash_table_new (g_str_hash, g_str_equal);
-
-       index = GPOINTER_TO_UINT (g_hash_table_lookup (w->file_to_index, name));
-       if (index > 0)
-               return index;
-
-       if (g_path_is_absolute (name)) {
-               char *dir = g_path_get_dirname (name);
-
-               if (!w->dir_to_index)
-                       w->dir_to_index = g_hash_table_new (g_str_hash, g_str_equal);
-
-               dir_index = GPOINTER_TO_UINT (g_hash_table_lookup (w->dir_to_index, dir));
-               if (dir_index == 0) {
-                       emit_section_change (w, ".debug_line", LINE_SUBSECTION_INCLUDES);
-                       emit_string (w, dir);
-
-                       dir_index = ++ w->line_number_dir_index;
-                       g_hash_table_insert (w->dir_to_index, g_strdup (dir), GUINT_TO_POINTER (dir_index));
-               }
-
-               g_free (dir);
-
-               basename = g_path_get_basename (name);
-       } else {
-               dir_index = 0;
-       }
-
-       emit_section_change (w, ".debug_line", LINE_SUBSECTION_FILES);
-
-       if (basename)
-               emit_string (w, basename);
-       else
-               emit_string (w, name);
-       emit_uleb128 (w, dir_index);
-       emit_byte (w, 0);
-       emit_byte (w, 0);
-
-       emit_section_change (w, ".debug_line", LINE_SUBSECTION_DATA);
-
-       if (basename)
-               g_free (basename);
-
-       index = ++ w->line_number_file_index;
-       g_hash_table_insert (w->file_to_index, g_strdup (name), GUINT_TO_POINTER (index));
-
-       return index;
-}
-
 static int
 get_line_number_file_name (MonoDwarfWriter *w, const char *name)
 {
@@ -734,8 +638,6 @@ emit_all_line_number_info (MonoDwarfWriter *w)
        GSList *l;
        GSList *info_list;
 
-       g_assert (w->collect_line_info);
-
        add_line_number_file_name (w, "<unknown>", 0, 0);
 
        /* Collect files */
@@ -887,6 +789,12 @@ mono_dwarf_writer_emit_base_info (MonoDwarfWriter *w, const char *cu_name, GSLis
        char *s, *build_info;
        int i;
 
+       if (!w->emit_line) {
+               emit_section_change (w, ".debug_line", 0);
+               emit_label (w, ".Ldebug_line_section_start");
+               emit_label (w, ".Ldebug_line_start");
+       }
+
        w->cie_program = base_unwind_program;
 
        emit_section_change (w, ".debug_abbrev", 0);
@@ -936,14 +844,6 @@ mono_dwarf_writer_emit_base_info (MonoDwarfWriter *w, const char *cu_name, GSLis
        emit_int32 (w, 0); /* .debug_abbrev offset */
        emit_byte (w, sizeof (gpointer)); /* address size */
 
-       if (mono_img_writer_subsections_supported (w->w) && w->appending) {
-               /* Emit this into a separate section so it gets placed at the end */
-               emit_section_change (w, ".debug_info", 1);
-               emit_byte (w, 0); /* close COMPILE_UNIT */
-               emit_label (w, ".Ldebug_info_end");
-               emit_section_change (w, ".debug_info", 0);
-       }
-
        /* Compilation unit */
        emit_uleb128 (w, ABBREV_COMPILE_UNIT);
        build_info = mono_get_runtime_build_info ();
@@ -957,10 +857,7 @@ mono_dwarf_writer_emit_base_info (MonoDwarfWriter *w, const char *cu_name, GSLis
        emit_pointer_value (w, 0);
        emit_pointer_value (w, 0);
        /* offset into .debug_line section */
-       if (w->emit_line)
-               emit_symbol_diff (w, ".Ldebug_line_start", ".Ldebug_line_section_start", 0);
-       else
-               emit_pointer_value (w, 0);
+       emit_symbol_diff (w, ".Ldebug_line_start", ".Ldebug_line_section_start", 0);
 
        /* Base types */
        for (i = 0; i < G_N_ELEMENTS (basic_types); ++i) {
@@ -988,13 +885,11 @@ mono_dwarf_writer_emit_base_info (MonoDwarfWriter *w, const char *cu_name, GSLis
 void
 mono_dwarf_writer_close (MonoDwarfWriter *w)
 {
-       if (!w->appending) {
-               emit_section_change (w, ".debug_info", 0);
-               emit_byte (w, 0); /* close COMPILE_UNIT */
-               emit_label (w, ".Ldebug_info_end");
-       }
+       emit_section_change (w, ".debug_info", 0);
+       emit_byte (w, 0); /* close COMPILE_UNIT */
+       emit_label (w, ".Ldebug_info_end");
 
-       if (w->collect_line_info)
+       if (w->emit_line)
                emit_all_line_number_info (w);
 }
 
@@ -1698,7 +1593,7 @@ emit_line_number_info (MonoDwarfWriter *w, MonoMethod *method,
                addr_diff = i - prev_native_offset;
 
                if (first) {    
-                       emit_section_change (w, ".debug_line", LINE_SUBSECTION_DATA);
+                       emit_section_change (w, ".debug_line", 0);
 
                        emit_byte (w, 0);
                        emit_byte (w, sizeof (gpointer) + 1);
@@ -1714,10 +1609,7 @@ emit_line_number_info (MonoDwarfWriter *w, MonoMethod *method,
                        if (!prev_file_name || strcmp (loc->source_file, prev_file_name) != 0) {
                                /* Add an entry to the file table */
                                /* FIXME: Avoid duplicates */
-                               if (w->collect_line_info)
-                                       file_index = get_line_number_file_name (w, loc->source_file) + 1;
-                               else
-                                       file_index = emit_line_number_file_name (w, loc->source_file, 0, 0);
+                               file_index = get_line_number_file_name (w, loc->source_file) + 1;
                                g_free (prev_file_name);
                                prev_file_name = g_strdup (loc->source_file);
 
@@ -1775,7 +1667,7 @@ emit_line_number_info (MonoDwarfWriter *w, MonoMethod *method,
 
                il_to_line = g_new0 (int, header->code_size);
 
-               emit_section_change (w, ".debug_line", LINE_SUBSECTION_DATA);
+               emit_section_change (w, ".debug_line", 0);
                emit_byte (w, 0);
                emit_byte (w, sizeof (gpointer) + 1);
                emit_byte (w, DW_LNE_set_address);
@@ -2072,23 +1964,18 @@ mono_dwarf_writer_emit_method (MonoDwarfWriter *w, MonoCompile *cfg, MonoMethod
                w->fde_index ++;
        }
 
-       /* Emit line number info */
+       /* Save the information needed to emit the line number info later at once */
        /* != could happen when using --regression */
        if (debug_info && (debug_info->code_start == code)) {
-               if (w->collect_line_info) {
-                       MethodLineNumberInfo *info;
-
-                       /* Save the information needed to emit the line number info later at once */
-                       info = g_new0 (MethodLineNumberInfo, 1);
-                       info->method = method;
-                       info->start_symbol = g_strdup (start_symbol);
-                       info->end_symbol = g_strdup (end_symbol);
-                       info->code = code;
-                       info->code_size = code_size;
-                       w->line_info = g_slist_prepend (w->line_info, info);
-               } else {
-                       emit_line_number_info (w, method, start_symbol, end_symbol, code, code_size, debug_info);
-               }
+               MethodLineNumberInfo *info;
+
+               info = g_new0 (MethodLineNumberInfo, 1);
+               info->method = method;
+               info->start_symbol = g_strdup (start_symbol);
+               info->end_symbol = g_strdup (end_symbol);
+               info->code = code;
+               info->code_size = code_size;
+               w->line_info = g_slist_prepend (w->line_info, info);
        }
 
        emit_line (w);
index b5a08b1e99042624b166466bdbf24c9f7a52d51b..83d6a1c16d5391e673984b8fdf4a3e5514edf5b9 100644 (file)
@@ -20,7 +20,7 @@
 
 typedef struct _MonoDwarfWriter MonoDwarfWriter;
 
-MonoDwarfWriter* mono_dwarf_writer_create (MonoImageWriter *writer, FILE *il_file, int il_file_start_line, gboolean appending, gboolean emit_line_numbers);
+MonoDwarfWriter* mono_dwarf_writer_create (MonoImageWriter *writer, FILE *il_file, int il_file_start_line, gboolean emit_line_numbers);
 
 void mono_dwarf_writer_destroy (MonoDwarfWriter *w);
 
index 1f4f63384ed3e2e93af6c0f8215c8de2a0146e44..06c0fd710fc830a14454225d2867b41b8823f999 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2001 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -306,18 +307,20 @@ mono_amd64_throw_exception (guint64 dummy1, guint64 dummy2, guint64 dummy3, guin
                                                        guint64 dummy5, guint64 dummy6,
                                                        MonoContext *mctx, MonoObject *exc, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
 
        /* mctx is on the caller's stack */
        memcpy (&ctx, mctx, sizeof (MonoContext));
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
 
        /* adjust eip so that it point into the call instruction */
        ctx.gregs [AMD64_RIP] --;
@@ -415,10 +418,7 @@ get_throw_trampoline (MonoTrampInfo **info, gboolean rethrow, gboolean corlib, g
        amd64_lea_membase (code, AMD64_RAX, AMD64_RSP, stack_size + sizeof(mgreg_t));
        amd64_mov_membase_reg (code, AMD64_RSP, regs_offset + (AMD64_RSP * sizeof(mgreg_t)), X86_EAX, sizeof(mgreg_t));
        /* Save IP */
-       if (llvm_abs)
-               amd64_alu_reg_reg (code, X86_XOR, AMD64_RAX, AMD64_RAX);
-       else
-               amd64_mov_reg_membase (code, AMD64_RAX, AMD64_RSP, stack_size, sizeof(mgreg_t));
+       amd64_mov_reg_membase (code, AMD64_RAX, AMD64_RSP, stack_size, sizeof(mgreg_t));
        amd64_mov_membase_reg (code, AMD64_RSP, regs_offset + (AMD64_RIP * sizeof(mgreg_t)), AMD64_RAX, sizeof(mgreg_t));
        /* Set arg1 == ctx */
        amd64_lea_membase (code, AMD64_RAX, AMD64_RSP, ctx_offset);
@@ -432,14 +432,14 @@ get_throw_trampoline (MonoTrampInfo **info, gboolean rethrow, gboolean corlib, g
        if (resume_unwind) {
                amd64_mov_membase_imm (code, AMD64_RSP, arg_offsets [2], 0, sizeof(mgreg_t));
        } else if (corlib) {
-               amd64_mov_membase_reg (code, AMD64_RSP, arg_offsets [2], AMD64_ARG_REG2, sizeof(mgreg_t));
                if (llvm_abs)
-                       /* 
-                        * The caller is LLVM code which passes the absolute address not a pc offset,
-                        * so compensate by passing 0 as 'rip' and passing the negated abs address as
-                        * the pc offset.
+                       /*
+                        * The caller doesn't pass in a pc/pc offset, instead we simply use the
+                        * caller ip. Negate the pc adjustment done in mono_amd64_throw_corlib_exception ().
                         */
-                       amd64_neg_membase (code, AMD64_RSP, arg_offsets [2]);
+                       amd64_mov_membase_imm (code, AMD64_RSP, arg_offsets [2], 1, sizeof(mgreg_t));
+               else
+                       amd64_mov_membase_reg (code, AMD64_RSP, arg_offsets [2], AMD64_ARG_REG2, sizeof(mgreg_t));
        } else {
                amd64_mov_membase_imm (code, AMD64_RSP, arg_offsets [2], rethrow, sizeof(mgreg_t));
        }
index b478a713bc5e108ea30e7d59ed5e4a2f8c24a9c0..4c2b5ce821db200b5cbb1765ac463eb54cde8463 100644 (file)
@@ -137,6 +137,7 @@ mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
 void
 mono_arm_throw_exception (MonoObject *exc, mgreg_t pc, mgreg_t sp, mgreg_t *int_regs, gdouble *fp_regs)
 {
+       MonoError error;
        MonoContext ctx;
        gboolean rethrow = sp & 1;
 
@@ -152,25 +153,27 @@ mono_arm_throw_exception (MonoObject *exc, mgreg_t pc, mgreg_t sp, mgreg_t *int_
        memcpy (((guint8*)&ctx.regs) + (ARMREG_R4 * sizeof (mgreg_t)), int_regs, 8 * sizeof (mgreg_t));
        memcpy (&ctx.fregs, fp_regs, sizeof (double) * 16);
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
        mono_handle_exception (&ctx, exc);
        mono_restore_context (&ctx);
        g_assert_not_reached ();
 }
 
 void
-mono_arm_throw_exception_by_token (guint32 type_token, mgreg_t pc, mgreg_t sp, mgreg_t *int_regs, gdouble *fp_regs)
+mono_arm_throw_exception_by_token (guint32 ex_token_index, mgreg_t pc, mgreg_t sp, mgreg_t *int_regs, gdouble *fp_regs)
 {
+       guint32 ex_token = MONO_TOKEN_TYPE_DEF | ex_token_index;
        /* Clear thumb bit */
        pc &= ~1;
 
-       mono_arm_throw_exception ((MonoObject*)mono_exception_from_token (mono_defaults.corlib, type_token), pc, sp, int_regs, fp_regs);
+       mono_arm_throw_exception ((MonoObject*)mono_exception_from_token (mono_defaults.corlib, ex_token), pc, sp, int_regs, fp_regs);
 }
 
 void
@@ -245,9 +248,15 @@ get_throw_trampoline (int size, gboolean corlib, gboolean rethrow, gboolean llvm
        /* exc is already in place in r0 */
        if (corlib) {
                /* The caller ip is already in R1 */
-               if (llvm)
-                       /* Negate the ip adjustment done in mono_arm_throw_exception */
-                       ARM_ADD_REG_IMM8 (code, ARMREG_R1, ARMREG_R1, 4);
+               if (llvm) {
+                       /*
+                        * The address passed by llvm might point to before the call,
+                        * thus outside the eh range recorded by llvm. Use the return
+                        * address instead.
+                        * FIXME: Do this on more platforms.
+                        */
+                       ARM_MOV_REG_REG (code, ARMREG_R1, ARMREG_LR); /* caller ip */
+               }
        } else {
                ARM_MOV_REG_REG (code, ARMREG_R1, ARMREG_LR); /* caller ip */
        }
index 333fd13b75420df017b11a5be0d7c2f41d32e56b..fe210faa3a22ce14883bcad17c657328cf8bd746 100644 (file)
@@ -1 +1,587 @@
-#include "../../../mono-extensions/mono/mini/exceptions-arm64.c"
+/*
+ * exceptions-arm64.c: exception support for ARM64
+ *
+ * Copyright 2013 Xamarin Inc
+ *
+ * Based on exceptions-arm.c:
+ *
+ * Authors:
+ *   Dietmar Maurer (dietmar@ximian.com)
+ *   Paolo Molaro (lupus@ximian.com)
+ *
+ * (C) 2001 Ximian, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+#include "mini.h"
+
+#include <mono/arch/arm64/arm64-codegen.h>
+#include <mono/metadata/abi-details.h>
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+#ifndef DISABLE_JIT
+
+gpointer
+mono_arch_get_restore_context (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *start, *code;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+       int i, ctx_reg, size;
+
+       size = 256;
+       code = start = mono_global_codeman_reserve (size);
+
+       arm_movx (code, ARMREG_IP0, ARMREG_R0);
+       ctx_reg = ARMREG_IP0;
+       /* Restore fregs */
+       for (i = 0; i < 32; ++i)
+               arm_ldrfpx (code, i, ctx_reg, MONO_STRUCT_OFFSET (MonoContext, fregs) + (i * 8));
+       /* Restore gregs */
+       // FIXME: Restore less registers
+       // FIXME: fp should be restored later
+       code = mono_arm_emit_load_regarray (code, 0xffffffff & ~(1 << ctx_reg) & ~(1 << ARMREG_SP), ctx_reg, MONO_STRUCT_OFFSET (MonoContext, regs));
+       /* ip0/ip1 doesn't need to be restored */
+       /* ip1 = pc */
+       arm_ldrx (code, ARMREG_IP1, ctx_reg, MONO_STRUCT_OFFSET (MonoContext, pc));
+       /* ip0 = sp */
+       arm_ldrx (code, ARMREG_IP0, ctx_reg, MONO_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_SP * 8));
+       /* Restore sp, ctx is no longer valid */
+       arm_movspx (code, ARMREG_SP, ARMREG_IP0); 
+       /* Branch to pc */
+       arm_brx (code, ARMREG_IP1);
+       /* Not reached */
+       arm_brk (code, 0);
+
+       g_assert ((code - start) < size);
+       mono_arch_flush_icache (start, code - start);
+       mono_profiler_code_buffer_new (start, code - start, MONO_PROFILER_CODE_BUFFER_EXCEPTION_HANDLING, NULL);
+
+       if (info)
+               *info = mono_tramp_info_create ("restore_context", start, code - start, ji, unwind_ops);
+
+       return start;
+}
+
+gpointer
+mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code;
+       guint8* start;
+       int size, offset, gregs_offset, fregs_offset, ctx_offset, num_fregs, frame_size;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+
+       size = 512;
+       start = code = mono_global_codeman_reserve (size);
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* frame block */
+       offset += 2 * 8;
+       /* gregs */
+       gregs_offset = offset;
+       offset += 32 * 8;
+       /* fregs */
+       num_fregs = 8;
+       fregs_offset = offset;
+       offset += num_fregs * 8;
+       ctx_offset = offset;
+       ctx_offset += 8;
+       frame_size = ALIGN_TO (offset, MONO_ARCH_FRAME_ALIGNMENT);
+
+       /*
+        * We are being called from C code, ctx is in r0, the address to call is in r1.
+        * We need to save state, restore ctx, make the call, then restore the previous state,
+        * returning the value returned by the call.
+        */
+
+       /* Setup a frame */
+       arm_stpx_pre (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, -frame_size);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+
+       /* Save ctx */
+       arm_strx (code, ARMREG_R0, ARMREG_FP, ctx_offset);
+       /* Save gregs */
+       code = mono_arm_emit_store_regarray (code, MONO_ARCH_CALLEE_SAVED_REGS | (1 << ARMREG_FP), ARMREG_FP, gregs_offset);
+       /* No need to save/restore fregs, since we don't currently use them */
+
+       /* Load regs from ctx */
+       code = mono_arm_emit_load_regarray (code, MONO_ARCH_CALLEE_SAVED_REGS, ARMREG_R0, MONO_STRUCT_OFFSET (MonoContext, regs));
+       /* Load fp */
+       arm_ldrx (code, ARMREG_FP, ARMREG_R0, MONO_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_FP * 8));
+
+       /* Make the call */
+       arm_blrx (code, ARMREG_R1);
+       /* For filters, the result is in R0 */
+
+       /* Restore fp */
+       arm_ldrx (code, ARMREG_FP, ARMREG_SP, gregs_offset + (ARMREG_FP * 8));
+       /* Load ctx */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_FP, ctx_offset);
+       /* Save registers back to ctx */
+       /* This isn't strictly neccessary since we don't allocate variables used in eh clauses to registers */
+       code = mono_arm_emit_store_regarray (code, MONO_ARCH_CALLEE_SAVED_REGS, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoContext, regs));
+
+       /* Restore regs */
+       code = mono_arm_emit_load_regarray (code, MONO_ARCH_CALLEE_SAVED_REGS, ARMREG_FP, gregs_offset);
+       /* Destroy frame */
+       code = mono_arm_emit_destroy_frame (code, frame_size, (1 << ARMREG_IP0));
+       arm_retx (code, ARMREG_LR);
+
+       g_assert ((code - start) < size);
+       mono_arch_flush_icache (start, code - start);
+       mono_profiler_code_buffer_new (start, code - start, MONO_PROFILER_CODE_BUFFER_EXCEPTION_HANDLING, NULL);
+
+       if (info)
+               *info = mono_tramp_info_create ("call_filter", start, code - start, ji, unwind_ops);
+
+       return start;
+}
+
+static gpointer 
+get_throw_trampoline (int size, gboolean corlib, gboolean rethrow, gboolean llvm, gboolean resume_unwind, const char *tramp_name, MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *start, *code;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+       int i, offset, gregs_offset, fregs_offset, frame_size, num_fregs;
+
+       code = start = mono_global_codeman_reserve (size);
+
+       /* We are being called by JITted code, the exception object/type token is in R0 */
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* frame block */
+       offset += 2 * 8;
+       /* gregs */
+       gregs_offset = offset;
+       offset += 32 * 8;
+       /* fregs */
+       num_fregs = 8;
+       fregs_offset = offset;
+       offset += num_fregs * 8;
+       frame_size = ALIGN_TO (offset, MONO_ARCH_FRAME_ALIGNMENT);
+
+       /* Setup a frame */
+       arm_stpx_pre (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, -frame_size);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+
+       /* Save gregs */
+       code = mono_arm_emit_store_regarray (code, 0xffffffff, ARMREG_FP, gregs_offset);
+       if (corlib && !llvm)
+               /* The real LR is in R1 */
+               arm_strx (code, ARMREG_R1, ARMREG_FP, gregs_offset + (ARMREG_LR * 8));
+       /* Save fp/sp */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_FP, 0);
+       arm_strx (code, ARMREG_IP0, ARMREG_FP, gregs_offset + (ARMREG_FP * 8));
+       arm_addx_imm (code, ARMREG_IP0, ARMREG_FP, frame_size);
+       arm_strx (code, ARMREG_IP0, ARMREG_FP, gregs_offset + (ARMREG_SP * 8)); 
+       /* Save fregs */
+       for (i = 0; i < num_fregs; ++i)
+               arm_strfpx (code, ARMREG_D8 + i, ARMREG_FP, fregs_offset + (i * 8));
+
+       /* Call the C trampoline function */
+       /* Arg1 =  exception object/type token */
+       arm_movx (code, ARMREG_R0, ARMREG_R0);
+       /* Arg2 = caller ip */
+       if (corlib) {
+               if (llvm)
+                       arm_ldrx (code, ARMREG_R1, ARMREG_FP, gregs_offset + (ARMREG_LR * 8));
+               else
+                       arm_movx (code, ARMREG_R1, ARMREG_R1);
+       } else {
+               arm_ldrx (code, ARMREG_R1, ARMREG_FP, 8);
+       }
+       /* Arg 3 = gregs */
+       arm_addx_imm (code, ARMREG_R2, ARMREG_FP, gregs_offset);
+       /* Arg 4 = fregs */
+       arm_addx_imm (code, ARMREG_R3, ARMREG_FP, fregs_offset);
+       /* Arg 5 = corlib */
+       arm_movzx (code, ARMREG_R4, corlib ? 1 : 0, 0);
+       /* Arg 6 = rethrow */
+       arm_movzx (code, ARMREG_R5, rethrow ? 1 : 0, 0);
+       /* Call the function */
+       if (aot) {
+               const char *icall_name;
+
+               if (resume_unwind)
+                       icall_name = "mono_arm_resume_unwind";
+               else
+                       icall_name = "mono_arm_throw_exception";
+
+               code = mono_arm_emit_aotconst (&ji, code, start, ARMREG_LR, MONO_PATCH_INFO_JIT_ICALL_ADDR, icall_name);
+       } else {
+               gpointer icall_func;
+
+               if (resume_unwind)
+                       icall_func = mono_arm_resume_unwind;
+               else
+                       icall_func = mono_arm_throw_exception;
+
+               code = mono_arm_emit_imm64 (code, ARMREG_LR, (guint64)icall_func);
+       }
+       arm_blrx (code, ARMREG_LR);
+       /* This shouldn't return */
+       arm_brk (code, 0x0);
+
+       g_assert ((code - start) < size);
+       mono_arch_flush_icache (start, code - start);
+       mono_profiler_code_buffer_new (start, code - start, MONO_PROFILER_CODE_BUFFER_EXCEPTION_HANDLING, NULL);
+
+       if (info)
+               *info = mono_tramp_info_create (tramp_name, start, code - start, ji, unwind_ops);
+
+       return start;
+}
+
+gpointer 
+mono_arch_get_throw_exception (MonoTrampInfo **info, gboolean aot)
+{
+       return get_throw_trampoline (256, FALSE, FALSE, FALSE, FALSE, "throw_exception", info, aot);
+}
+
+gpointer
+mono_arch_get_rethrow_exception (MonoTrampInfo **info, gboolean aot)
+{
+       return get_throw_trampoline (256, FALSE, TRUE, FALSE, FALSE, "rethrow_exception", info, aot);
+}
+
+gpointer 
+mono_arch_get_throw_corlib_exception (MonoTrampInfo **info, gboolean aot)
+{
+       return get_throw_trampoline (256, TRUE, FALSE, FALSE, FALSE, "throw_corlib_exception", info, aot);
+}
+
+GSList*
+mono_arm_get_exception_trampolines (gboolean aot)
+{
+       MonoTrampInfo *info;
+       GSList *tramps = NULL;
+
+       /* LLVM uses the normal trampolines, but with a different name */
+       get_throw_trampoline (256, TRUE, FALSE, FALSE, FALSE, "llvm_throw_corlib_exception_trampoline", &info, aot);
+       tramps = g_slist_prepend (tramps, info);
+       
+       get_throw_trampoline (256, TRUE, FALSE, TRUE, FALSE, "llvm_throw_corlib_exception_abs_trampoline", &info, aot);
+       tramps = g_slist_prepend (tramps, info);
+
+       get_throw_trampoline (256, FALSE, FALSE, FALSE, TRUE, "llvm_resume_unwind_trampoline", &info, aot);
+       tramps = g_slist_prepend (tramps, info);
+
+       return tramps;
+}
+
+#else /* DISABLE_JIT */
+
+gpointer
+mono_arch_get_restore_context (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer 
+mono_arch_get_throw_exception (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_rethrow_exception (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer 
+mono_arch_get_throw_corlib_exception (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}      
+
+GSList*
+mono_arm_get_exception_trampolines (gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif /* !DISABLE_JIT */
+
+void
+mono_arch_exceptions_init (void)
+{
+       guint8 *tramp;
+       GSList *tramps, *l;
+
+       if (mono_aot_only) {
+               tramp = mono_aot_get_trampoline ("llvm_throw_corlib_exception_trampoline");
+               mono_register_jit_icall (tramp, "llvm_throw_corlib_exception_trampoline", NULL, TRUE);
+               tramp = mono_aot_get_trampoline ("llvm_throw_corlib_exception_abs_trampoline");
+               mono_register_jit_icall (tramp, "llvm_throw_corlib_exception_abs_trampoline", NULL, TRUE);
+               tramp = mono_aot_get_trampoline ("llvm_resume_unwind_trampoline");
+               mono_register_jit_icall (tramp, "llvm_resume_unwind_trampoline", NULL, TRUE);
+       } else {
+               tramps = mono_arm_get_exception_trampolines (FALSE);
+               for (l = tramps; l; l = l->next) {
+                       MonoTrampInfo *info = l->data;
+
+                       mono_register_jit_icall (info->code, g_strdup (info->name), NULL, TRUE);
+                       mono_tramp_info_register (info, NULL);
+               }
+               g_slist_free (tramps);
+       }
+}
+
+/*
+ * mono_arm_throw_exception:
+ *
+ *   This function is called by the exception trampolines.
+ * FP_REGS points to the 8 callee saved fp regs.
+ */
+void
+mono_arm_throw_exception (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp_regs, gboolean corlib, gboolean rethrow)
+{
+       MonoError error;
+       MonoContext ctx;
+       MonoObject *exc = NULL;
+       guint32 ex_token_index, ex_token;
+
+       if (!corlib)
+               exc = arg;
+       else {
+               ex_token_index = (guint64)arg;
+               ex_token = MONO_TOKEN_TYPE_DEF | ex_token_index;
+               exc = (MonoObject*)mono_exception_from_token (mono_defaults.corlib, ex_token);
+       }
+
+       /* Adjust pc so it points into the call instruction */
+       pc -= 4;
+
+       /* Initialize a ctx based on the arguments */
+       memset (&ctx, 0, sizeof (MonoContext));
+       memcpy (&(ctx.regs [0]), int_regs, sizeof (mgreg_t) * 32);
+       memcpy (&(ctx.fregs [ARMREG_D8]), fp_regs, sizeof (double) * 8);
+       ctx.pc = pc;
+
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
+               MonoException *mono_ex = (MonoException*)exc;
+               if (!rethrow) {
+                       mono_ex->stack_trace = NULL;
+                       mono_ex->trace_ips = NULL;
+               }
+       }
+       mono_error_assert_ok (&error);
+
+       mono_handle_exception (&ctx, exc);
+
+       mono_restore_context (&ctx);
+}
+
+void
+mono_arm_resume_unwind (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp_regs, gboolean corlib, gboolean rethrow)
+{
+       MonoContext ctx;
+
+       /* Adjust pc so it points into the call instruction */
+       pc -= 4;
+
+       /* Initialize a ctx based on the arguments */
+       memset (&ctx, 0, sizeof (MonoContext));
+       memcpy (&(ctx.regs [0]), int_regs, sizeof (mgreg_t) * 32);
+       memcpy (&(ctx.fregs [ARMREG_D8]), fp_regs, sizeof (double) * 8);
+       ctx.pc = pc;
+
+       mono_resume_unwind (&ctx);
+}
+
+/* 
+ * mono_arch_unwind_frame:
+ *
+ * See exceptions-amd64.c for docs;
+ */
+gboolean
+mono_arch_unwind_frame (MonoDomain *domain, MonoJitTlsData *jit_tls, 
+                                                        MonoJitInfo *ji, MonoContext *ctx, 
+                                                        MonoContext *new_ctx, MonoLMF **lmf,
+                                                        mgreg_t **save_locations,
+                                                        StackFrameInfo *frame)
+{
+       gpointer ip = MONO_CONTEXT_GET_IP (ctx);
+
+       memset (frame, 0, sizeof (StackFrameInfo));
+       frame->ji = ji;
+
+       *new_ctx = *ctx;
+
+       if (ji != NULL) {
+               mgreg_t regs [MONO_MAX_IREGS + 8 + 1];
+               guint8 *cfa;
+               guint32 unwind_info_len;
+               guint8 *unwind_info;
+
+               frame->type = FRAME_TYPE_MANAGED;
+
+               unwind_info = mono_jinfo_get_unwind_info (ji, &unwind_info_len);
+
+               memcpy (regs, &new_ctx->regs, sizeof (mgreg_t) * 32);
+               /* v8..v15 are callee saved */
+               memcpy (regs + MONO_MAX_IREGS, &(new_ctx->fregs [8]), sizeof (mgreg_t) * 8);
+
+               mono_unwind_frame (unwind_info, unwind_info_len, ji->code_start, 
+                                                  (guint8*)ji->code_start + ji->code_size,
+                                                  ip, NULL, regs, MONO_MAX_IREGS + 8,
+                                                  save_locations, MONO_MAX_IREGS, &cfa);
+
+               memcpy (&new_ctx->regs, regs, sizeof (mgreg_t) * 32);
+               memcpy (&(new_ctx->fregs [8]), regs + MONO_MAX_IREGS, sizeof (mgreg_t) * 8);
+
+               new_ctx->pc = regs [ARMREG_LR];
+               new_ctx->regs [ARMREG_SP] = (mgreg_t)cfa;
+
+               if (*lmf && (*lmf)->gregs [MONO_ARCH_LMF_REG_SP] && (MONO_CONTEXT_GET_SP (ctx) >= (gpointer)(*lmf)->gregs [MONO_ARCH_LMF_REG_SP])) {
+                       /* remove any unused lmf */
+                       *lmf = (gpointer)(((gsize)(*lmf)->previous_lmf) & ~3);
+               }
+
+               /* we substract 1, so that the IP points into the call instruction */
+               new_ctx->pc--;
+
+               return TRUE;
+       } else if (*lmf) {
+               if (((gsize)(*lmf)->previous_lmf) & 2) {
+                       /* 
+                        * This LMF entry is created by the soft debug code to mark transitions to
+                        * managed code done during invokes.
+                        */
+                       MonoLMFExt *ext = (MonoLMFExt*)(*lmf);
+
+                       g_assert (ext->debugger_invoke);
+
+                       memcpy (new_ctx, &ext->ctx, sizeof (MonoContext));
+
+                       *lmf = (gpointer)(((gsize)(*lmf)->previous_lmf) & ~3);
+
+                       frame->type = FRAME_TYPE_DEBUGGER_INVOKE;
+
+                       return TRUE;
+               }
+
+               frame->type = FRAME_TYPE_MANAGED_TO_NATIVE;
+
+               ji = mini_jit_info_table_find (domain, (gpointer)(*lmf)->pc, NULL);
+               if (!ji)
+                       return FALSE;
+
+               g_assert (MONO_ARCH_LMF_REGS == ((0x3ff << 19) | (1 << ARMREG_FP) | (1 << ARMREG_SP)));
+               memcpy (&new_ctx->regs [ARMREG_R19], &(*lmf)->gregs [0], sizeof (mgreg_t) * 10);
+               new_ctx->regs [ARMREG_FP] = (*lmf)->gregs [MONO_ARCH_LMF_REG_FP];
+               new_ctx->regs [ARMREG_SP] = (*lmf)->gregs [MONO_ARCH_LMF_REG_SP];
+               new_ctx->pc = (*lmf)->pc;
+
+               /* we substract 1, so that the IP points into the call instruction */
+               new_ctx->pc--;
+
+               *lmf = (gpointer)(((gsize)(*lmf)->previous_lmf) & ~3);
+
+               return TRUE;
+       }
+
+       return FALSE;
+}
+
+/*
+ * handle_exception:
+ *
+ *   Called by resuming from a signal handler.
+ */
+static void
+handle_signal_exception (gpointer obj)
+{
+       MonoJitTlsData *jit_tls = mono_native_tls_get_value (mono_jit_tls_id);
+       MonoContext ctx;
+
+       memcpy (&ctx, &jit_tls->ex_ctx, sizeof (MonoContext));
+
+       mono_handle_exception (&ctx, obj);
+
+       mono_restore_context (&ctx);
+}
+
+/*
+ * This is the function called from the signal handler
+ */
+gboolean
+mono_arch_handle_exception (void *ctx, gpointer obj)
+{
+#if defined(MONO_CROSS_COMPILE)
+       g_assert_not_reached ();
+#else
+       MonoJitTlsData *jit_tls;
+       void *sigctx = ctx;
+
+       /*
+        * Resume into the normal stack and handle the exception there.
+        */
+       jit_tls = mono_native_tls_get_value (mono_jit_tls_id);
+
+       /* Pass the ctx parameter in TLS */
+       mono_sigctx_to_monoctx (sigctx, &jit_tls->ex_ctx);
+       /* The others in registers */
+       UCONTEXT_REG_R0 (sigctx) = (gsize)obj;
+
+       UCONTEXT_REG_PC (sigctx) = (gsize)handle_signal_exception;
+       UCONTEXT_REG_SP (sigctx) = UCONTEXT_REG_SP (sigctx) - MONO_ARCH_REDZONE_SIZE;
+#endif
+
+       return TRUE;
+}
+
+gpointer
+mono_arch_ip_from_context (void *sigctx)
+{
+#ifdef MONO_CROSS_COMPILE
+       g_assert_not_reached ();
+       return NULL;
+#else
+       return (gpointer)UCONTEXT_REG_PC (sigctx);
+#endif
+}
+
+void
+mono_arch_setup_async_callback (MonoContext *ctx, void (*async_cb)(void *fun), gpointer user_data)
+{
+       mgreg_t sp = (mgreg_t)MONO_CONTEXT_GET_SP (ctx);
+
+       // FIXME:
+       g_assert (!user_data);
+
+       /* Allocate a stack frame */
+       sp -= 32;
+       MONO_CONTEXT_SET_SP (ctx, sp);
+
+       mono_arch_setup_resume_sighandler_ctx (ctx, async_cb);
+}
+
+/*
+ * mono_arch_setup_resume_sighandler_ctx:
+ *
+ *   Setup CTX so execution continues at FUNC.
+ */
+void
+mono_arch_setup_resume_sighandler_ctx (MonoContext *ctx, gpointer func)
+{
+       MONO_CONTEXT_SET_IP (ctx,func);
+}
index 9d13bfbf2c59a3f485e4a2d963cda406fb4caf04..adae20f2b5f2fb83a57d67b3b08b30a77f007483 100644 (file)
@@ -236,18 +236,20 @@ static void
 throw_exception (MonoObject *exc, guint64 rethrow)
 {
        unw_context_t unw_ctx;
+       MonoError error;
        MonoContext ctx;
        MonoJitInfo *ji;
        unw_word_t ip, sp;
        int res;
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
 
        res = unw_getcontext (&unw_ctx);
        g_assert (res == 0);
index f8d9dedff2ce60e3e223f4189b57c5452a456c4d..f39ff46977a8ce5d25c8ed7e89c2b16dde67b163 100644 (file)
@@ -176,6 +176,7 @@ mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
 static void
 throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
 
 #ifdef DEBUG_EXCEPTIONS
@@ -194,13 +195,14 @@ throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp, gboolean
        memset (&ctx.sc_fpregs, 0, sizeof (mips_freg) * MONO_SAVED_FREGS);
        MONO_CONTEXT_SET_IP (&ctx, eip);
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
        mono_handle_exception (&ctx, exc);
 #ifdef DEBUG_EXCEPTIONS
        g_print ("throw_exception: restore to pc=%p sp=%p fp=%p ctx=%p\n",
index 1088e12ea426ae53272624cb11c3a49de19e8863..80a579b05eb87e539e3b1c344edf636991b4c667 100644 (file)
@@ -318,6 +318,7 @@ mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
 void
 mono_ppc_throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp, mgreg_t *int_regs, gdouble *fp_regs, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
 
        /* adjust eip so that it point into the call instruction */
@@ -331,13 +332,14 @@ mono_ppc_throw_exception (MonoObject *exc, unsigned long eip, unsigned long esp,
        memcpy (&ctx.regs, int_regs, sizeof (mgreg_t) * MONO_SAVED_GREGS);
        memcpy (&ctx.fregs, fp_regs, sizeof (double) * MONO_SAVED_FREGS);
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
        mono_handle_exception (&ctx, exc);
        mono_restore_context (&ctx);
 
index 18e51bd94ee89b6743184d8aa915007f03bdd010..fc2390d0b8596511ce63b68edea34504b213e227 100644 (file)
@@ -13,6 +13,7 @@
 /*              Dietmar Maurer (dietmar@ximian.com)                */
 /*                                                                 */
 /* Copyright   - 2001 Ximian, Inc.                                 */
+/* Licensed under the MIT license. See LICENSE file in the project root for full license information. */
 /*                                                                 */
 /*------------------------------------------------------------------*/
 
@@ -240,6 +241,7 @@ throw_exception (MonoObject *exc, unsigned long ip, unsigned long sp,
                 gulong *int_regs, gdouble *fp_regs, gint32 *acc_regs, 
                 guint fpc, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
        int iReg;
 
@@ -261,13 +263,14 @@ throw_exception (MonoObject *exc, unsigned long ip, unsigned long sp,
        MONO_CONTEXT_SET_BP (&ctx, sp);
        MONO_CONTEXT_SET_IP (&ctx, ip);
        
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
 //     mono_arch_handle_exception (&ctx, exc, FALSE);
        mono_handle_exception (&ctx, exc);
        mono_restore_context(&ctx);
index d9b3d9d99c658bfc396ef0e01aa21af3633d7a03..77510a7f934de0d832dd20fca39c687f19c4d1de 100644 (file)
@@ -166,6 +166,7 @@ mono_arch_get_call_filter (MonoTrampInfo **info, gboolean aot)
 static void
 throw_exception (MonoObject *exc, gpointer sp, gpointer ip, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
        static void (*restore_context) (MonoContext *);
        gpointer *window;
@@ -178,13 +179,14 @@ throw_exception (MonoObject *exc, gpointer sp, gpointer ip, gboolean rethrow)
        ctx.ip = ip;
        ctx.fp = (gpointer*)(MONO_SPARC_WINDOW_ADDR (sp) [sparc_i6 - 16]);
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
        mono_handle_exception (&ctx, exc);
        restore_context (&ctx);
 
index 87a67abd930f3d4ee33149018d6a2ed89ca38fb1..14e8f6111c15ce90bac97f37ab15c38b85ec27ae 100644 (file)
@@ -456,6 +456,7 @@ void
 mono_x86_throw_exception (mgreg_t *regs, MonoObject *exc, 
                                                  mgreg_t eip, gboolean rethrow)
 {
+       MonoError error;
        MonoContext ctx;
 
        ctx.esp = regs [X86_ESP];
@@ -473,13 +474,14 @@ mono_x86_throw_exception (mgreg_t *regs, MonoObject *exc,
        g_assert ((ctx.esp % MONO_ARCH_FRAME_ALIGNMENT) == 0);
 #endif
 
-       if (mono_object_isinst (exc, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (exc, mono_defaults.exception_class, &error)) {
                MonoException *mono_ex = (MonoException*)exc;
                if (!rethrow) {
                        mono_ex->stack_trace = NULL;
                        mono_ex->trace_ips = NULL;
                }
        }
+       mono_error_assert_ok (&error);
 
        /* adjust eip so that it point into the call instruction */
        ctx.eip -= 1;
index b996f8f83b55a07a401a31409d4f5c437228d43c..21f87eb5819d7a47a4e0ca63cf739666226b79bb 100644 (file)
@@ -54,6 +54,14 @@ static GHashTable *template_table;
 
 #define eat_whitespace(s) while (*(s) && isspace (*(s))) s++;
 
+// Per spec isalnum() expects input in the range 0-255
+// and can misbehave if you pass in a signed char.
+static int
+isalnum_char(char c)
+{
+       return isalnum ((unsigned char)c);
+}
+
 static int
 load_file (const char *name) {
        FILE *f;
@@ -163,7 +171,7 @@ load_file (const char *name) {
                                OpDesc *tdesc;
                                p += 9;
                                tname = p;
-                               while (*p && isalnum (*p)) ++p;
+                               while (*p && isalnum_char (*p)) ++p;
                                *p++ = 0;
                                tdesc = (OpDesc *)g_hash_table_lookup (template_table, tname);
                                if (!tdesc)
@@ -181,7 +189,7 @@ load_file (const char *name) {
                                        g_error ("Duplicated name tag in template %s at '%s' at line %d in %s\n", desc->name, p, line, name);
                                p += 5;
                                tname = p;
-                               while (*p && isalnum (*p)) ++p;
+                               while (*p && isalnum_char (*p)) ++p;
                                *p++ = 0;
                                if (g_hash_table_lookup (template_table, tname))
                                        g_error ("Duplicated template %s at line %d in %s\n", tname, line, name);
@@ -195,6 +203,7 @@ load_file (const char *name) {
                if (is_template && !desc->name)
                        g_error ("Template without name at line %d in %s\n", line, name);
        }
+       g_string_free (comment,TRUE);
        fclose (f);
        return 0;
 }
@@ -220,7 +229,7 @@ init_table (void) {
 
 static void
 output_char (FILE *f, char c) {
-       if (isalnum (c))
+       if (isalnum_char (c))
                fprintf (f, "%c", c);
        else
                fprintf (f, "\\x%x\" \"", (guint8)c);
index a8bfee03414ab95fe515d69c2dce3f7b178af86a..88f8c2ebb22b780a3c461daf2d8b62e6370f3e68 100644 (file)
@@ -1716,6 +1716,23 @@ public class Tests
                return 0;
        }
 
+       interface ISmallArg {
+               T foo<T> (string s1, string s2, string s3, string s4, string s5, string s6, string s7, string s8,
+                                 string s9, string s10, string s11, string s12, string s13, T t);
+       }
+
+       class SmallArgClass : ISmallArg {
+                       public T foo<T> (string s1, string s2, string s3, string s4, string s5, string s6, string s7, string s8,
+                                                        string s9, string s10, string s11, string s12, string s13, T t) {
+                               return t;
+                       }
+               }
+
+       public static int test_1_small_gsharedvt_stack_arg_ios () {
+               ISmallArg o = new SmallArgClass ();
+               return o.foo<int> ("", "", "", "", "", "", "", "", "", "", "", "", "", 1);
+       }
+
        // Passing vtype normal arguments on the stack
        public static int test_0_arm64_vtype_stack_args () {
                IFoo3<EmptyStruct> o = (IFoo3<EmptyStruct>)Activator.CreateInstance (typeof (Foo3<>).MakeGenericType (new Type [] { typeof (EmptyStruct) }));
index c216f3b25755f4231091b096a4f506990e4a8d2f..4992565ba0d162951515dee73e1177f56124f4f8 100644 (file)
@@ -1686,6 +1686,9 @@ bin_writer_emit_writeout (MonoImageWriter *acfg)
 static void
 asm_writer_emit_start (MonoImageWriter *acfg)
 {
+#if defined(TARGET_ASM_APPLE)
+       fprintf (acfg->fp, ".subsections_via_symbols\n");
+#endif
 }
 
 static int
@@ -1759,8 +1762,14 @@ asm_writer_emit_symbol_type (MonoImageWriter *acfg, const char *name, gboolean f
                stype = "object";
 
        asm_writer_emit_unset_mode (acfg);
+
 #if defined(TARGET_ASM_APPLE)
 
+#elif defined(TARGET_WIN32)
+       if (func)
+               fprintf (acfg->fp, "\t.def %s; .scl 2; .type 32; .endef\n", name);
+       else
+               fprintf (acfg->fp, "\t.data\n");
 #elif defined(TARGET_ARM)
        fprintf (acfg->fp, "\t.type %s,#%s\n", name, stype);
 #else
@@ -1783,7 +1792,7 @@ asm_writer_emit_local_symbol (MonoImageWriter *acfg, const char *name, const cha
 {
        asm_writer_emit_unset_mode (acfg);
 
-#ifndef TARGET_ASM_APPLE
+#if !defined(TARGET_ASM_APPLE) && !defined(TARGET_WIN32)
        fprintf (acfg->fp, "\t.local %s\n", name);
 #endif
 
@@ -1795,7 +1804,8 @@ asm_writer_emit_symbol_size (MonoImageWriter *acfg, const char *name, const char
 {
        asm_writer_emit_unset_mode (acfg);
 
-#ifndef TARGET_ASM_APPLE
+
+#if !defined(TARGET_ASM_APPLE) && !defined(TARGET_WIN32)
        fprintf (acfg->fp, "\t.size %s,%s-%s\n", name, end_label, name);
 #endif
 }
index b67cb5f1508f03a58db4225668c10980ab0da4c0..6d87c74e92d01e1fb087a6f8c19e57dc65084c08 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright 2003-2011 Novell Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <math.h>
@@ -102,11 +103,14 @@ mono_ldvirtfn_gshared (MonoObject *obj, MonoMethod *method)
 void
 mono_helper_stelem_ref_check (MonoArray *array, MonoObject *val)
 {
+       MonoError error;
        if (!array) {
                mono_set_pending_exception (mono_get_exception_null_reference ());
                return;
        }
-       if (val && !mono_object_isinst (val, array->obj.vtable->klass->element_class)) {
+       if (val && !mono_object_isinst_checked (val, array->obj.vtable->klass->element_class, &error)) {
+               if (mono_error_set_pending_exception (&error))
+                       return;
                mono_set_pending_exception (mono_get_exception_array_type_mismatch ());
                return;
        }
@@ -1178,6 +1182,7 @@ mono_create_corlib_exception_2 (guint32 token, MonoString *arg1, MonoString *arg
 MonoObject*
 mono_object_castclass_unbox (MonoObject *obj, MonoClass *klass)
 {
+       MonoError error;
        MonoJitTlsData *jit_tls = NULL;
        MonoClass *oklass;
 
@@ -1192,8 +1197,10 @@ mono_object_castclass_unbox (MonoObject *obj, MonoClass *klass)
        oklass = obj->vtable->klass;
        if ((klass->enumtype && oklass == klass->element_class) || (oklass->enumtype && klass == oklass->element_class))
                return obj;
-       if (mono_object_isinst (obj, klass))
+       if (mono_object_isinst_checked (obj, klass, &error))
                return obj;
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (mini_get_debug_options ()->better_cast_details) {
                jit_tls->class_cast_from = oklass;
@@ -1209,6 +1216,7 @@ mono_object_castclass_unbox (MonoObject *obj, MonoClass *klass)
 MonoObject*
 mono_object_castclass_with_cache (MonoObject *obj, MonoClass *klass, gpointer *cache)
 {
+       MonoError error;
        MonoJitTlsData *jit_tls = NULL;
        gpointer cached_vtable, obj_vtable;
 
@@ -1226,10 +1234,12 @@ mono_object_castclass_with_cache (MonoObject *obj, MonoClass *klass, gpointer *c
        if (cached_vtable == obj_vtable)
                return obj;
 
-       if (mono_object_isinst (obj, klass)) {
+       if (mono_object_isinst_checked (obj, klass, &error)) {
                *cache = obj_vtable;
                return obj;
        }
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        if (mini_get_debug_options ()->better_cast_details) {
                jit_tls->class_cast_from = obj->vtable->klass;
@@ -1245,6 +1255,7 @@ mono_object_castclass_with_cache (MonoObject *obj, MonoClass *klass, gpointer *c
 MonoObject*
 mono_object_isinst_with_cache (MonoObject *obj, MonoClass *klass, gpointer *cache)
 {
+       MonoError error;
        size_t cached_vtable, obj_vtable;
 
        if (!obj)
@@ -1257,10 +1268,12 @@ mono_object_isinst_with_cache (MonoObject *obj, MonoClass *klass, gpointer *cach
                return (cached_vtable & 0x1) ? NULL : obj;
        }
 
-       if (mono_object_isinst (obj, klass)) {
+       if (mono_object_isinst_checked (obj, klass, &error)) {
                *cache = (gpointer)obj_vtable;
                return obj;
        } else {
+               if (mono_error_set_pending_exception (&error))
+                       return NULL;
                /*negative cache*/
                *cache = (gpointer)(obj_vtable | 0x1);
                return NULL;
@@ -1322,7 +1335,7 @@ constrained_gsharedvt_call_setup (gpointer mp, MonoMethod *cmethod, MonoClass *k
                /*
                 * Calling a non-vtype method with a vtype receiver, has to box.
                 */
-               *this_arg = mono_value_box (mono_domain_get (), klass, mp);
+               *this_arg = mono_value_box_checked (mono_domain_get (), klass, mp, error);
        else if (klass->valuetype)
                /*
                 * Calling a vtype method with a vtype receiver
index f26d6597bb52b970dcdef31455f800478e39cd59..c897893074057b178071b619e5420ae7a36b5b6e 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 6a7c49c0629f85bca6005c0976241ffd6cb06830..7fef6b85cb9741b955d701ae1082822fea5cca66 100644 (file)
@@ -4,7 +4,7 @@
 // (C) 2009-2011 Novell, Inc.
 // Copyright 2011-2015 Xamarin, Inc (http://www.xamarin.com)
 //
-
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 // Mono's internal header files are not C++ clean, so avoid including them if 
 // possible
index 2120fa08728e6c39a3863b4ab80ce95dc3c5b499..32cd496f30f19b43817bfef49cfe95f27a2d5a08 100644 (file)
@@ -10,6 +10,7 @@
  *
  * (C) 2006 Novell, Inc.  http://www.novell.com
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -180,6 +181,69 @@ mono_strength_reduction_ins (MonoCompile *cfg, MonoInst *ins, const char **spec)
 #endif
                break;
        }
+#if SIZEOF_REGISTER == 4
+       case OP_LSHR_IMM: {
+               if (ins->inst_c1 == 32) {
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (ins->dreg), MONO_LVREG_MS (ins->sreg1));
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1), 31);
+               } else if (ins->inst_c1 == 0) {
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1));
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1));
+               } else if (ins->inst_c1 > 32) {
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_IMM, MONO_LVREG_LS (ins->dreg), MONO_LVREG_MS (ins->sreg1), ins->inst_c1 - 32);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1), 31);
+               } else {
+                       guint32 tmpreg = alloc_ireg (cfg);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHL_IMM, tmpreg, MONO_LVREG_MS (ins->sreg1), 32 - ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_UN_IMM, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU (cfg, OP_IOR, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->dreg), tmpreg);
+                       allocated_vregs = TRUE;
+               }
+               break;
+       }
+       case OP_LSHR_UN_IMM: {
+               if (ins->inst_c1 == 32) {
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (ins->dreg), MONO_LVREG_MS (ins->sreg1));
+                       MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_MS (ins->dreg), 0);
+               } else if (ins->inst_c1 == 0) {
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1));
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1));
+               } else if (ins->inst_c1 > 32) {
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_UN_IMM, MONO_LVREG_LS (ins->dreg), MONO_LVREG_MS (ins->sreg1), ins->inst_c1 - 32);
+                       MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_MS (ins->dreg), 0);
+               } else {
+                       guint32 tmpreg = alloc_ireg (cfg);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHL_IMM, tmpreg, MONO_LVREG_MS (ins->sreg1), 32 - ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_UN_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_UN_IMM, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU (cfg, OP_IOR, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->dreg), tmpreg);
+                       allocated_vregs = TRUE;
+               }
+               break;
+       }
+       case OP_LSHL_IMM: {
+               if (ins->inst_c1 == 32) {
+                       /* just move the lower half to the upper and zero the lower word */
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_MS (ins->dreg), MONO_LVREG_LS (ins->sreg1));
+                       MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_LS (ins->dreg), 0);
+               } else if (ins->inst_c1 == 0) {
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1));
+                       MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1));
+               } else if (ins->inst_c1 > 32) {
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHL_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_LS (ins->sreg1), ins->inst_c1 - 32);
+                       MONO_EMIT_NEW_ICONST (cfg, MONO_LVREG_LS (ins->dreg), 0);
+               } else {
+                       guint32 tmpreg = alloc_ireg (cfg);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHR_UN_IMM, tmpreg, MONO_LVREG_LS (ins->sreg1), 32 - ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHL_IMM, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU_IMM (cfg, OP_ISHL_IMM, MONO_LVREG_LS (ins->dreg), MONO_LVREG_LS (ins->sreg1), ins->inst_c1);
+                       MONO_EMIT_NEW_BIALU (cfg, OP_IOR, MONO_LVREG_MS (ins->dreg), MONO_LVREG_MS (ins->dreg), tmpreg);
+                       allocated_vregs = TRUE;
+               }
+               break;
+       }
+#endif
 
        default:
                break;
index 4ef344ecdd9b0f1b5e005e5e9a1f6b258744dadb..de8ab61e3d5b64550e733981fcce690c013d7860 100644 (file)
@@ -1,10 +1,18 @@
 #include <config.h>
+#include <fcntl.h>
+#include <mono/metadata/assembly.h>
+#include <mono/utils/mono-mmap.h>
 #include "mini.h"
 
-#ifndef HOST_WIN32
-#ifndef BUILDVER_INCLUDED
-#include "buildver-boehm.h"
+#ifdef HAVE_UNISTD_H
+#  include <unistd.h>
 #endif
+#ifdef HOST_WIN32
+#  include <io.h>
+#else
+#  ifndef BUILDVER_INCLUDED
+#    include "buildver-boehm.h"
+#  endif
 #endif
 
 /*
@@ -20,6 +28,114 @@ mono_main_with_options (int argc, char *argv [])
        return mono_main (argc, argv);
 }
 
+#define STREAM_INT(x) (*(uint32_t*)x)
+#define STREAM_LONG(x) (*(uint64_t*)x)
+
+static gboolean
+probe_embedded (const char *program, int *ref_argc, char **ref_argv [])
+{
+       MonoBundledAssembly last = { NULL, 0, 0 };
+       char sigbuffer [16+sizeof (uint64_t)];
+       gboolean status = FALSE;
+       uint64_t directory_location;
+       off_t sigstart, baseline = 0;
+       uint64_t directory_size;
+       char *directory, *p;
+       int items, i;
+       unsigned char *mapaddress = NULL;
+       void *maphandle = NULL;
+       GArray *assemblies;
+       char *entry_point = NULL;
+       char **new_argv;
+       int j;
+
+       int fd = open (program, O_RDONLY);
+       if (fd == -1)
+               return FALSE;
+       if ((sigstart = lseek (fd, -(16+sizeof(uint64_t)), SEEK_END)) == -1)
+               goto doclose;
+       if (read (fd, sigbuffer, sizeof (sigbuffer)) == -1)
+               goto doclose;
+       if (memcmp (sigbuffer+sizeof(uint64_t), "xmonkeysloveplay", 16) != 0)
+               goto doclose;
+       directory_location = GUINT64_FROM_LE ((*(uint64_t *) &sigbuffer [0]));
+       if (lseek (fd, directory_location, SEEK_SET) == -1)
+               goto doclose;
+       directory_size = sigstart-directory_location;
+       directory = g_malloc (directory_size);
+       if (directory == NULL)
+               goto doclose;
+       if (read (fd, directory, directory_size) == -1)
+               goto dofree;
+
+       items = STREAM_INT (directory);
+       p = directory+4;
+
+       assemblies = g_array_new (0, 0, sizeof (MonoBundledAssembly*));
+       for (i = 0; i < items; i++){
+               char *kind;
+               int strsize = STREAM_INT (p);
+               uint64_t offset, item_size;
+               kind = p+4;
+               p += 4 + strsize;
+               offset = STREAM_LONG(p);
+               p += 8;
+               item_size = STREAM_INT (p);
+               p += 4;
+               
+               if (mapaddress == NULL){
+                       mapaddress = mono_file_map (directory_location-offset, MONO_MMAP_READ | MONO_MMAP_PRIVATE, fd, offset, &maphandle);
+                       if (mapaddress == NULL){
+                               perror ("Error mapping file");
+                               exit (1);
+                       }
+                       baseline = offset;
+               }
+               if (strncmp (kind, "assembly:", strlen ("assembly:")) == 0){
+                       char *aname = kind + strlen ("assembly:");
+                       MonoBundledAssembly mba = { aname, mapaddress + offset - baseline, item_size }, *ptr;
+                       ptr = g_new (MonoBundledAssembly, 1);
+                       memcpy (ptr, &mba, sizeof (MonoBundledAssembly));
+                       g_array_append_val  (assemblies, ptr);
+                       if (entry_point == NULL)
+                               entry_point = aname;
+               } else if (strncmp (kind, "config:", strlen ("config:")) == 0){
+                       printf ("c-Found: %s %llx\n", kind, offset);
+                       char *config = kind + strlen ("config:");
+                       char *aname = g_strdup (config);
+                       aname [strlen(aname)-strlen(".config")] = 0;
+                       mono_register_config_for_assembly (aname, config);
+               } else if (strncmp (kind, "system_config:", strlen ("system_config:")) == 0){
+                       printf ("TODO s-Found: %s %llx\n", kind, offset);
+               } else if (strncmp (kind, "options:", strlen ("options:")) == 0){
+                       mono_parse_options_from (kind + strlen("options:"), ref_argc, ref_argv);
+               } else if (strncmp (kind, "config_dir:", strlen ("config_dir:")) == 0){
+                       printf ("TODO Found: %s %llx\n", kind, offset);
+               } else {
+                       fprintf (stderr, "Unknown stream on embedded package: %s\n", kind);
+                       exit (1);
+               }
+       }
+       g_array_append_val (assemblies, last);
+       
+       mono_register_bundled_assemblies ((const MonoBundledAssembly **) assemblies->data);
+       new_argv = g_new (char *, (*ref_argc)+1);
+       for (j = 0; j < *ref_argc; j++)
+               new_argv [j] = (*ref_argv)[j];
+       new_argv [j] = entry_point;
+       *ref_argv = new_argv;
+       (*ref_argc)++;
+       
+       return TRUE;
+       
+dofree:
+       g_free (directory);
+doclose:
+       if (!status)
+               close (fd);
+       return status;
+}
+
 #ifdef HOST_WIN32
 
 #include <shellapi.h>
@@ -27,11 +143,13 @@ mono_main_with_options (int argc, char *argv [])
 int
 main (void)
 {
+       TCHAR szFileName[MAX_PATH];
        int argc;
        gunichar2** argvw;
        gchar** argv;
        int i;
-
+       DWORD count;
+       
        argvw = CommandLineToArgvW (GetCommandLine (), &argc);
        argv = g_new0 (gchar*, argc + 1);
        for (i = 0; i < argc; i++)
@@ -40,6 +158,11 @@ main (void)
 
        LocalFree (argvw);
 
+       if ((count = GetModuleFileName (NULL, szFileName, MAX_PATH)) != 0){
+               char *entry = g_utf16_to_utf8 (szFileName, count, NULL, NULL, NULL);
+               probe_embedded (entry, &argc, &argv);
+       }
+
        return mono_main_with_options  (argc, argv);
 }
 
@@ -49,7 +172,8 @@ int
 main (int argc, char* argv[])
 {
        mono_build_date = build_date;
-       
+
+       probe_embedded (argv [0], &argc, &argv);
        return mono_main_with_options (argc, argv);
 }
 
index 3d295db2a358a479cdce82160444b1066145b036..8e6ffa8dbac0d62df121c2d96d0082607b974e21 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2002 Ximian, Inc.
  * Copyright 2003-2010 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -4229,7 +4230,7 @@ handle_alloc (MonoCompile *cfg, MonoClass *klass, gboolean for_box, int context_
                                if (size < sizeof (MonoObject))
                                        g_error ("Invalid size %d for class %s", size, mono_type_get_full_name (klass));
 
-                               EMIT_NEW_ICONST (cfg, iargs [1], mono_gc_get_aligned_size_for_allocator (size));
+                               EMIT_NEW_ICONST (cfg, iargs [1], size);
                        }
                        return mono_emit_method_call (cfg, managed_alloc, iargs, NULL);
                }
@@ -4266,7 +4267,7 @@ handle_alloc (MonoCompile *cfg, MonoClass *klass, gboolean for_box, int context_
                                g_error ("Invalid size %d for class %s", size, mono_type_get_full_name (klass));
 
                        EMIT_NEW_VTABLECONST (cfg, iargs [0], vtable);
-                       EMIT_NEW_ICONST (cfg, iargs [1], mono_gc_get_aligned_size_for_allocator (size));
+                       EMIT_NEW_ICONST (cfg, iargs [1], size);
                        return mono_emit_method_call (cfg, managed_alloc, iargs, NULL);
                }
                alloc_ftn = mono_class_get_allocation_ftn (vtable, for_box, &pass_lw);
@@ -7260,7 +7261,6 @@ inline_method (MonoCompile *cfg, MonoMethod *cmethod, MonoMethodSignature *fsig,
                if (cfg->verbose_level > 2)
                        printf ("INLINE ABORTED %s (cost %d)\n", mono_method_full_name (cmethod, TRUE), costs);
                cfg->exception_type = MONO_EXCEPTION_NONE;
-               mono_loader_clear_error ();
 
                /* This gets rid of the newly added bblocks */
                cfg->cbb = prev_cbb;
@@ -8578,7 +8578,7 @@ mono_method_to_ir (MonoCompile *cfg, MonoMethod *method, MonoBasicBlock *start_b
 
        skip_dead_blocks = !dont_verify;
        if (skip_dead_blocks) {
-               original_bb = bb = mono_basic_block_split (method, &cfg->error);
+               original_bb = bb = mono_basic_block_split (method, &cfg->error, header);
                CHECK_CFG_ERROR;
                g_assert (bb);
        }
@@ -11649,7 +11649,6 @@ mono_method_to_ir (MonoCompile *cfg, MonoMethod *method, MonoBasicBlock *start_b
                                                                INLINE_FAILURE ("class init");
                                                        if (!mono_runtime_class_init_full (vtable, &cfg->error)) {
                                                                mono_cfg_set_exception (cfg, MONO_EXCEPTION_MONO_ERROR);
-                                                               g_assert_not_reached ();
                                                                goto exception_exit;
                                                        }
                                                }
@@ -11870,7 +11869,7 @@ mono_method_to_ir (MonoCompile *cfg, MonoMethod *method, MonoBasicBlock *start_b
                                        EMIT_NEW_CLASSCONST (cfg, iargs [1], klass);
                                        iargs [2] = sp [0];
 
-                                       ins = mono_emit_jit_icall (cfg, mono_array_new, iargs);
+                                       ins = mono_emit_jit_icall (cfg, ves_icall_array_new, iargs);
                                } else {
                                        /* Decompose later since it is needed by abcrem */
                                        MonoClass *array_type = mono_array_class_get (klass, 1);
diff --git a/mono/mini/mini-amd64-gsharedvt.c b/mono/mini/mini-amd64-gsharedvt.c
new file mode 100644 (file)
index 0000000..dffa937
--- /dev/null
@@ -0,0 +1,478 @@
+/*
+ * mini-amd64-gsharedvt.c: libcorkscrew-based native unwinder
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *   Rodrigo Kumpera <kumpera@gmail.com>
+ *   Andi McClure <andi.mcclure@xamarin.com>
+ *
+ * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <config.h>
+#include <glib.h>
+
+#include <mono/metadata/abi-details.h>
+#include <mono/metadata/appdomain.h>
+#include <mono/metadata/marshal.h>
+#include <mono/metadata/tabledefs.h>
+#include <mono/metadata/mono-debug-debugger.h>
+#include <mono/metadata/profiler-private.h>
+#include <mono/metadata/gc-internals.h>
+#include <mono/arch/amd64/amd64-codegen.h>
+
+#include <mono/utils/memcheck.h>
+
+#include "mini.h"
+#include "mini-amd64.h"
+#include "mini-amd64-gsharedvt.h"
+#include "debugger-agent.h"
+
+#if defined (MONO_ARCH_GSHAREDVT_SUPPORTED)
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+gboolean
+mono_arch_gsharedvt_sig_supported (MonoMethodSignature *sig)
+{
+       return FALSE;
+}
+
+static const char*
+storage_name (ArgStorage st)
+{
+       switch (st) {
+       case ArgInIReg: return "ArgInIReg";
+       case ArgInFloatSSEReg: return "ArgInFloatSSEReg";
+       case ArgInDoubleSSEReg: return "ArgInDoubleSSEReg";
+       case ArgOnStack: return "ArgOnStack";
+       case ArgValuetypeInReg: return "ArgValuetypeInReg";
+       case ArgValuetypeAddrInIReg: return "ArgValuetypeAddrInIReg";
+       case ArgGSharedVtInReg: return "ArgGSharedVtInReg";
+       case ArgGSharedVtOnStack: return "ArgGSharedVtOnStack";
+       case ArgNone: return "ArgNone";
+       default: return "unknown";
+       }
+}
+
+static char *
+arg_info_desc (ArgInfo *info)
+{
+       GString *str = g_string_new ("");
+
+       g_string_append_printf (str, "offset %d reg %s storage %s nregs %d", info->offset, mono_arch_regname (info->reg), storage_name (info->storage), info->nregs);
+       if (info->storage == ArgValuetypeInReg)
+               g_string_append_printf (str, " {(%s %s), (%s %s)", 
+                       storage_name (info->pair_storage [0]),
+                       mono_arch_regname (info->pair_regs [0]),
+                       storage_name (info->pair_storage [1]),
+                       mono_arch_regname (info->pair_regs [1]));
+
+       return g_string_free (str, FALSE);
+}
+
+static inline void
+add_to_map (GPtrArray *map, int src, int dst)
+{
+       g_ptr_array_add (map, GUINT_TO_POINTER (src));
+       g_ptr_array_add (map, GUINT_TO_POINTER (dst));
+}
+
+/*
+ * Slot mapping:
+ * 0..5  - rdi, rsi, rdx, rcx, r8, r9
+ * 6..13 - xmm0..xmm7
+ * 14..  - stack slots
+ */
+static inline int
+map_reg (int reg)
+{
+       int i = 0;
+       for (i = 0; i < PARAM_REGS; ++i) {
+               if (param_regs [i] == reg)
+                       return i;
+       }
+       g_error ("Invalid argument register number %d", reg);
+       return -1;
+}
+
+static inline int
+map_freg (int reg)
+{
+       return reg + PARAM_REGS;
+}
+
+static inline int
+map_stack_slot (int slot)
+{
+       return slot + PARAM_REGS + FLOAT_PARAM_REGS;
+}
+
+/*
+Format for the source descriptor:
+
+
+Format for the destination descriptor:
+       bits 0:15  - source register
+       bits 16:23 - return marshal
+       bits 24:32 - slot count
+*/
+#define SRC_DESCRIPTOR_MARSHAL_SHIFT 16
+#define SRC_DESCRIPTOR_MARSHAL_MASK 0x0Ff
+
+#define SLOT_COUNT_SHIFT 24
+#define SLOT_COUNT_MASK 0xff
+#define SLOT_BYTE_SIZE 8
+
+static int
+get_arg_slots (ArgInfo *ainfo, int **out_slots, gboolean is_source_argument)
+{
+       int sreg = ainfo->reg;
+       int sslot = ainfo->offset / 8;
+       int *src = NULL;
+       int i, nsrc;
+
+       switch (ainfo->storage) {
+       case ArgInIReg:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_reg (sreg);
+               break;
+       case ArgValuetypeInReg:
+               nsrc = ainfo->nregs;
+               src = g_malloc (nsrc * sizeof (int));
+               for (i = 0; i < ainfo->nregs; ++i)
+                       src [i] = map_reg (ainfo->pair_regs [i]);
+               break;
+       case ArgOnStack:
+               nsrc = ainfo->arg_size / SLOT_BYTE_SIZE;
+               src = g_malloc (nsrc * sizeof (int));
+               // is_source_argument adds 2 because we're skipping over the old BBP and the return address
+               // XXX this is a very fragile setup as changes in alignment for the caller reg array can cause the magic number be 3
+               for (i = 0; i < nsrc; ++i)
+                       src [i] = map_stack_slot (sslot + i + (is_source_argument ? 2 : 0));
+               break;
+       case ArgInDoubleSSEReg:
+       case ArgInFloatSSEReg:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_freg (sreg);
+               break;
+       default:
+               NOT_IMPLEMENTED;
+               break;
+       }
+
+       *out_slots = src;
+       return nsrc;
+}
+
+// Once src is known, operate on the dst
+static void
+handle_marshal_when_src_gsharedvt (ArgInfo *dst_info, int *arg_marshal, int *arg_slots)
+{
+       switch (dst_info->storage) {
+               case ArgInIReg:
+               case ArgInDoubleSSEReg:
+               case ArgInFloatSSEReg:
+                       *arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL;
+                       *arg_slots = 1;
+                       break;
+               case ArgOnStack:
+                       *arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL;
+                       g_assert (dst_info->arg_size % SLOT_BYTE_SIZE == 0); // Assert quadword aligned
+                       *arg_slots = dst_info->arg_size / SLOT_BYTE_SIZE;
+                       break;
+               case ArgValuetypeInReg:
+                       *arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL;
+                       *arg_slots = dst_info->nregs;
+                       break;
+               default:
+                       NOT_IMPLEMENTED; // Inappropriate value: if dst and src are gsharedvt at once, we shouldn't be here
+                       break;
+       }
+}
+
+// Once dst is known, operate on the src
+static void
+handle_marshal_when_dst_gsharedvt (ArgInfo *src_info, int *arg_marshal)
+{
+       switch (src_info->storage) {
+               case ArgInIReg:
+               case ArgInDoubleSSEReg:
+               case ArgInFloatSSEReg:
+               case ArgValuetypeInReg:
+               case ArgOnStack:
+                       *arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF;
+                       break;
+               default:
+                       NOT_IMPLEMENTED; // See above
+                       break;
+       }
+}
+
+static void
+handle_map_when_gsharedvt_in_reg (ArgInfo *reg_info, int *n, int **map)
+{
+       *n = 1;
+       *map = g_new0 (int, 1);
+       (*map) [0] = map_reg (reg_info->reg);
+}
+
+static void
+handle_map_when_gsharedvt_on_stack (ArgInfo *reg_info, int *n, int **map, gboolean is_source_argument)
+{
+       *n = 1;
+       *map = g_new0 (int, 1);
+       int sslot = reg_info->offset / SLOT_BYTE_SIZE;
+       (*map) [0] = map_stack_slot (sslot + (is_source_argument ? 2 : 0)); // see get_arg_slots
+}
+
+gpointer
+mono_arch_get_gsharedvt_call_info (gpointer addr, MonoMethodSignature *normal_sig, MonoMethodSignature *gsharedvt_sig, gboolean gsharedvt_in, gint32 vcall_offset, gboolean calli)
+{
+       GSharedVtCallInfo *info;
+       CallInfo *caller_cinfo, *callee_cinfo;
+       MonoMethodSignature *caller_sig, *callee_sig;
+       int aindex, i;
+       gboolean var_ret = FALSE;
+       CallInfo *cinfo, *gcinfo;
+       MonoMethodSignature *sig, *gsig;
+       GPtrArray *map;
+
+       if (gsharedvt_in) {
+               caller_sig = normal_sig;
+               callee_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+       } else {
+               callee_sig = normal_sig;
+               caller_sig = gsharedvt_sig;
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+       }
+
+       /*
+        * If GSHAREDVT_IN is true, this means we are transitioning from normal to gsharedvt code. The caller uses the
+        * normal call signature, while the callee uses the gsharedvt signature.
+        * If GSHAREDVT_IN is false, its the other way around.
+        */
+
+       /* sig/cinfo describes the normal call, while gsig/gcinfo describes the gsharedvt call */
+       if (gsharedvt_in) {
+               sig = caller_sig;
+               gsig = callee_sig;
+               cinfo = caller_cinfo;
+               gcinfo = callee_cinfo;
+       } else {
+               sig = callee_sig;
+               gsig = caller_sig;
+               cinfo = callee_cinfo;
+               gcinfo = caller_cinfo;
+       }
+
+       DEBUG_AMD64_GSHAREDVT_PRINT ("source sig: (%s) return (%s)\n", mono_signature_get_desc (caller_sig, FALSE), mono_type_full_name (mono_signature_get_return_type (caller_sig))); // Leak
+       DEBUG_AMD64_GSHAREDVT_PRINT ("dest sig: (%s) return (%s)\n", mono_signature_get_desc (callee_sig, FALSE), mono_type_full_name (mono_signature_get_return_type (callee_sig)));
+
+       if (gcinfo->ret.storage == ArgGsharedvtVariableInReg) {
+               /*
+                * The return type is gsharedvt
+                */
+               var_ret = TRUE;
+       }
+
+       /*
+        * The stack looks like this:
+        * <arguments>
+        * <trampoline frame>
+        * <call area>
+        * We have to map the stack slots in <arguments> to the stack slots in <call area>.
+        */
+       map = g_ptr_array_new ();
+
+       for (aindex = 0; aindex < cinfo->nargs; ++aindex) {
+               ArgInfo *src_info = &caller_cinfo->args [aindex];
+               ArgInfo *dst_info = &callee_cinfo->args [aindex];
+               int *src = NULL, *dst = NULL;
+               int nsrc = -1, ndst = -1, nslots = 0;
+
+               int arg_marshal = GSHAREDVT_ARG_NONE;
+               int arg_slots = 0; // Size in quadwords
+               DEBUG_AMD64_GSHAREDVT_PRINT ("-- arg %d in (%s) out (%s)\n", aindex, arg_info_desc (src_info), arg_info_desc (dst_info));
+
+               switch (src_info->storage) {
+               case ArgInIReg:
+               case ArgInDoubleSSEReg:
+               case ArgInFloatSSEReg:
+               case ArgValuetypeInReg:
+               case ArgOnStack:
+                       nsrc = get_arg_slots (src_info, &src, TRUE);
+                       break;
+               case ArgGSharedVtInReg:
+                       handle_marshal_when_src_gsharedvt (dst_info, &arg_marshal, &arg_slots);
+                       handle_map_when_gsharedvt_in_reg (src_info, &nsrc, &src);
+                       break;
+               case ArgGSharedVtOnStack:
+                       handle_marshal_when_src_gsharedvt (dst_info, &arg_marshal, &arg_slots);
+                       handle_map_when_gsharedvt_on_stack (src_info, &nsrc, &src, TRUE);
+                       break;
+               default:
+                       g_error ("Gsharedvt can't handle source arg type %d", (int)src_info->storage); // Inappropriate value: ArgValuetypeAddrInIReg is for returns only
+               }
+
+               switch (dst_info->storage) {
+               case ArgInIReg:
+               case ArgInDoubleSSEReg:
+               case ArgInFloatSSEReg:
+               case ArgOnStack:
+               case ArgValuetypeInReg:
+                       ndst = get_arg_slots (dst_info, &dst, FALSE);
+                       break;
+               case ArgGSharedVtInReg:
+                       handle_marshal_when_dst_gsharedvt (src_info, &arg_marshal);
+                       handle_map_when_gsharedvt_in_reg (dst_info, &ndst, &dst);
+                       break;
+               case ArgGSharedVtOnStack:
+                       handle_marshal_when_dst_gsharedvt (src_info, &arg_marshal);
+                       handle_map_when_gsharedvt_on_stack (dst_info, &ndst, &dst, FALSE);
+                       break;
+               default:
+                       g_error ("Gsharedvt can't handle dest arg type %d", (int)dst_info->storage); // See above
+               }
+               if (nsrc)
+                       src [0] |= (arg_marshal << SRC_DESCRIPTOR_MARSHAL_SHIFT) | (arg_slots << SLOT_COUNT_SHIFT);
+
+               /* Merge and add to the global list*/
+               nslots = MIN (nsrc, ndst);
+               DEBUG_AMD64_GSHAREDVT_PRINT ("nsrc %d ndst %d\n", nsrc, ndst);
+
+               for (i = 0; i < nslots; ++i)
+                       add_to_map (map, src [i], dst [i]);
+
+               g_free (src);
+               g_free (dst);
+       }
+
+       DEBUG_AMD64_GSHAREDVT_PRINT ("-- return in (%s) out (%s) var_ret %d\n", arg_info_desc (&caller_cinfo->ret),  arg_info_desc (&callee_cinfo->ret), var_ret);
+
+       if (cinfo->ret.storage == ArgValuetypeAddrInIReg) {
+               /* Both the caller and the callee pass the vtype ret address in r8 */
+               g_assert (gcinfo->ret.storage == ArgValuetypeAddrInIReg || gcinfo->ret.storage == ArgGsharedvtVariableInReg);
+               add_to_map (map, map_reg (cinfo->ret.reg), map_reg (cinfo->ret.reg));
+       }
+
+       info = mono_domain_alloc0 (mono_domain_get (), sizeof (GSharedVtCallInfo) + (map->len * sizeof (int)));
+       info->addr = addr;
+       info->stack_usage = callee_cinfo->stack_usage;
+       info->ret_marshal = GSHAREDVT_RET_NONE;
+       info->gsharedvt_in = gsharedvt_in ? 1 : 0;
+       info->vret_slot = -1;
+       info->calli = calli;
+
+       if (var_ret) {
+               g_assert (gcinfo->ret.storage == ArgGsharedvtVariableInReg);
+               info->vret_arg_reg = map_reg (gcinfo->ret.reg);
+               DEBUG_AMD64_GSHAREDVT_PRINT ("mapping vreg_arg_reg to %d in reg %s\n", info->vret_arg_reg, mono_arch_regname (gcinfo->ret.reg));
+       } else {
+               info->vret_arg_reg = -1;
+       }
+
+#ifdef DEBUG_AMD64_GSHAREDVT
+       printf ("final map:\n");
+       for (i = 0; i < map->len; i += 2) {
+               printf ("\t[%d] src %x dst %x\n ", 
+                       i / 2,
+                       GPOINTER_TO_UINT (g_ptr_array_index (map, i)),
+                       GPOINTER_TO_UINT (g_ptr_array_index (map, i + 1)));
+       }
+#endif
+
+       info->vcall_offset = vcall_offset;
+       info->map_count = map->len / 2;
+       for (i = 0; i < map->len; ++i)
+               info->map [i] = GPOINTER_TO_UINT (g_ptr_array_index (map, i));
+       g_ptr_array_free (map, TRUE);
+
+       /* Compute return value marshalling */
+       if (var_ret) {
+               /* Compute return value marshalling */
+               switch (cinfo->ret.storage) {
+               case ArgInIReg:
+                       if (!gsharedvt_in || sig->ret->byref) {
+                               info->ret_marshal = GSHAREDVT_RET_IREGS_1;
+                       } else {
+                               MonoType *ret = sig->ret;
+
+                               // Unwrap enums
+                               if (ret->type == MONO_TYPE_VALUETYPE)
+                                       ret = mini_type_get_underlying_type (ret);
+
+                               switch (ret->type) {
+                               case MONO_TYPE_I1:
+                                       info->ret_marshal = GSHAREDVT_RET_I1;
+                                       break;
+                               case MONO_TYPE_BOOLEAN:
+                               case MONO_TYPE_U1:
+                                       info->ret_marshal = GSHAREDVT_RET_U1;
+                                       break;
+                               case MONO_TYPE_I2:
+                                       info->ret_marshal = GSHAREDVT_RET_I2;
+                                       break;
+                               case MONO_TYPE_CHAR:
+                               case MONO_TYPE_U2:
+                                       info->ret_marshal = GSHAREDVT_RET_U2;
+                                       break;
+                               case MONO_TYPE_I4:
+                                       info->ret_marshal = GSHAREDVT_RET_I4;
+                                       break;
+                               case MONO_TYPE_U4:
+                                       info->ret_marshal = GSHAREDVT_RET_U4;
+                                       break;
+                               case MONO_TYPE_I:
+                               case MONO_TYPE_U:
+                               case MONO_TYPE_PTR:
+                               case MONO_TYPE_FNPTR:
+                               case MONO_TYPE_CLASS:
+                               case MONO_TYPE_OBJECT:
+                               case MONO_TYPE_SZARRAY:
+                               case MONO_TYPE_ARRAY:
+                               case MONO_TYPE_STRING:
+                               case MONO_TYPE_U8:
+                               case MONO_TYPE_I8:
+                                       info->ret_marshal = GSHAREDVT_RET_I8;
+                                       break;
+
+                               default:
+                                       g_error ("Gsharedvt can't handle dst type [%d]", (int)sig->ret->type);
+                               }
+                       }
+                       break;
+               case ArgValuetypeInReg:
+                       info->ret_marshal = GSHAREDVT_RET_IREGS_1 - 1 + cinfo->ret.nregs;
+                       g_assert (cinfo->ret.nregs == 1); // ABI supports 2-register return but we do not implement this.
+                       break;
+               case ArgInDoubleSSEReg:
+               case ArgInFloatSSEReg:
+                       info->ret_marshal = GSHAREDVT_RET_R8;
+                       break;
+               case ArgValuetypeAddrInIReg:
+                       break;
+               default:
+                       g_error ("Can't marshal return of storage [%d] %s", (int)cinfo->ret.storage, storage_name (cinfo->ret.storage));
+               }
+
+               if (gsharedvt_in && cinfo->ret.storage != ArgValuetypeAddrInIReg) {
+                       /* Allocate stack space for the return value */
+                       info->vret_slot = map_stack_slot (info->stack_usage / sizeof (gpointer));
+                       info->stack_usage += mono_type_stack_size_internal (normal_sig->ret, NULL, FALSE) + sizeof (gpointer);
+               }
+               DEBUG_AMD64_GSHAREDVT_PRINT ("RET marshal is %s\n", ret_marshal_name [info->ret_marshal]);
+       }
+
+       info->stack_usage = ALIGN_TO (info->stack_usage, MONO_ARCH_FRAME_ALIGNMENT);
+
+       DEBUG_AMD64_GSHAREDVT_PRINT ("allocated an info at %p stack usage %d\n", info, info->stack_usage);
+       return info;
+}
+
+#endif
diff --git a/mono/mini/mini-amd64-gsharedvt.h b/mono/mini/mini-amd64-gsharedvt.h
new file mode 100644 (file)
index 0000000..3e3d56c
--- /dev/null
@@ -0,0 +1,55 @@
+/*
+ * mini-exceptions-native-unwinder.c: libcorkscrew-based native unwinder
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *   Rodrigo Kumpera <kumpera@gmail.com>
+ *   Andi McClure <andi.mcclure@xamarin.com>
+ *
+ * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#ifndef MINI_AMD64_GSHAREDVT_H
+#define MINI_AMD64_GSHAREDVT_H
+
+typedef enum {
+       GSHAREDVT_ARG_NONE = 0,
+       GSHAREDVT_ARG_BYVAL_TO_BYREF,
+       GSHAREDVT_ARG_BYREF_TO_BYVAL,
+} GSharedVtArgMarshal;
+
+typedef enum {
+       GSHAREDVT_RET_NONE = 0,
+       GSHAREDVT_RET_I1,      // 1 byte integer
+       GSHAREDVT_RET_U1,      // 1 byte unsigned
+       GSHAREDVT_RET_I2,      // 2 byte integer
+       GSHAREDVT_RET_U2,      // 2 byte unsigned
+       GSHAREDVT_RET_I4,      // 4 byte integer
+       GSHAREDVT_RET_U4,      // 4 byte unsigned
+       GSHAREDVT_RET_I8,      // 8 byte integer
+       GSHAREDVT_RET_IREGS_1, // Load in first return register
+       GSHAREDVT_RET_R8,     // Double
+       GSHAREDVT_RET_NUM,
+} GSharedVtRetMarshal;
+
+static const char* ret_marshal_name[] = {
+       "GSHAREDVT_RET_NONE",
+       "GSHAREDVT_RET_I1",
+       "GSHAREDVT_RET_U1",
+       "GSHAREDVT_RET_I2",
+       "GSHAREDVT_RET_U2",
+       "GSHAREDVT_RET_I4",
+       "GSHAREDVT_RET_U4",
+       "GSHAREDVT_RET_I8",
+       "GSHAREDVT_RET_IREGS_1",
+       "GSHAREDVT_RET_R8",
+       "GSHAREDVT_RET_NUM",
+};
+
+#ifdef DEBUG_AMD64_GSHAREDVT
+#define DEBUG_AMD64_GSHAREDVT_PRINT printf
+#else
+#define DEBUG_AMD64_GSHAREDVT_PRINT(...)
+#endif
+
+#endif /* MINI_AMD64_GSHAREDVT_H */
\ No newline at end of file
index 5b386a904f0f8a97c929a2093aaf70b5109d3102..901a6c99d76554f74d5ef72cec3a828b6e0802c8 100644 (file)
@@ -12,6 +12,7 @@
  * (C) 2003 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "mini.h"
 #include <string.h>
@@ -479,48 +480,6 @@ mono_amd64_patch (unsigned char* code, gpointer target)
        amd64_patch (code, target);
 }
 
-typedef enum {
-       ArgInIReg,
-       ArgInFloatSSEReg,
-       ArgInDoubleSSEReg,
-       ArgOnStack,
-       ArgValuetypeInReg,
-       ArgValuetypeAddrInIReg,
-       /* gsharedvt argument passed by addr */
-       ArgGSharedVtInReg,
-       ArgGSharedVtOnStack,
-       ArgNone /* only in pair_storage */
-} ArgStorage;
-
-typedef struct {
-       gint16 offset;
-       gint8  reg;
-       ArgStorage storage : 8;
-       gboolean is_gsharedvt_return_value : 1;
-
-       /* Only if storage == ArgValuetypeInReg */
-       ArgStorage pair_storage [2];
-       gint8 pair_regs [2];
-       /* The size of each pair (bytes) */
-       int pair_size [2];
-       int nregs;
-       /* Only if storage == ArgOnStack */
-       int arg_size; // Bytes, will always be rounded up/aligned to 8 byte boundary
-} ArgInfo;
-
-typedef struct {
-       int nargs;
-       guint32 stack_usage;
-       guint32 reg_usage;
-       guint32 freg_usage;
-       gboolean need_stack_align;
-       /* The index of the vret arg in the argument list */
-       int vret_arg_index;
-       ArgInfo ret;
-       ArgInfo sig_cookie;
-       ArgInfo args [1];
-} CallInfo;
-
 #define DEBUG(a) if (cfg->verbose_level > 1) a
 
 static void inline
@@ -1149,6 +1108,7 @@ get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
                cinfo = (CallInfo *)g_malloc0 (sizeof (CallInfo) + (sizeof (ArgInfo) * n));
 
        cinfo->nargs = n;
+       cinfo->gsharedvt = mini_is_gsharedvt_variable_signature (sig);
 
        gr = 0;
        fr = 0;
@@ -1199,8 +1159,7 @@ get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
                        break;
                }
                if (mini_is_gsharedvt_type (ret_type)) {
-                       cinfo->ret.storage = ArgValuetypeAddrInIReg;
-                       cinfo->ret.is_gsharedvt_return_value = 1;
+                       cinfo->ret.storage = ArgGsharedvtVariableInReg;
                        break;
                }
                /* fall through */
@@ -1215,8 +1174,7 @@ get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
        case MONO_TYPE_VAR:
        case MONO_TYPE_MVAR:
                g_assert (mini_is_gsharedvt_type (ret_type));
-               cinfo->ret.storage = ArgValuetypeAddrInIReg;
-               cinfo->ret.is_gsharedvt_return_value = 1;
+               cinfo->ret.storage = ArgGsharedvtVariableInReg;
                break;
        case MONO_TYPE_VOID:
                break;
@@ -1232,7 +1190,8 @@ get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
         * are sometimes made using calli without sig->hasthis set, like in the delegate
         * invoke wrappers.
         */
-       if (cinfo->ret.storage == ArgValuetypeAddrInIReg && !is_pinvoke && (sig->hasthis || (sig->param_count > 0 && MONO_TYPE_IS_REFERENCE (mini_get_underlying_type (sig->params [0]))))) {
+       ArgStorage ret_storage = cinfo->ret.storage;
+       if ((ret_storage == ArgValuetypeAddrInIReg || ret_storage == ArgGsharedvtVariableInReg) && !is_pinvoke && (sig->hasthis || (sig->param_count > 0 && MONO_TYPE_IS_REFERENCE (mini_get_underlying_type (sig->params [0]))))) {
                if (sig->hasthis) {
                        add_general (&gr, &stack_size, cinfo->args + 0);
                } else {
@@ -1240,16 +1199,16 @@ get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
                        pstart = 1;
                }
                add_general (&gr, &stack_size, &cinfo->ret);
-               cinfo->ret.storage = ArgValuetypeAddrInIReg;
+               cinfo->ret.storage = ret_storage;
                cinfo->vret_arg_index = 1;
        } else {
                /* this */
                if (sig->hasthis)
                        add_general (&gr, &stack_size, cinfo->args + 0);
 
-               if (cinfo->ret.storage == ArgValuetypeAddrInIReg) {
+               if (ret_storage == ArgValuetypeAddrInIReg || ret_storage == ArgGsharedvtVariableInReg) {
                        add_general (&gr, &stack_size, &cinfo->ret);
-                       cinfo->ret.storage = ArgValuetypeAddrInIReg;
+                       cinfo->ret.storage = ret_storage;
                }
        }
 
@@ -1465,7 +1424,7 @@ mono_arch_init (void)
        mono_aot_register_jit_icall ("mono_amd64_throw_corlib_exception", mono_amd64_throw_corlib_exception);
        mono_aot_register_jit_icall ("mono_amd64_resume_unwind", mono_amd64_resume_unwind);
        mono_aot_register_jit_icall ("mono_amd64_get_original_ip", mono_amd64_get_original_ip);
-#if defined(ENABLE_GSHAREDVT)
+#if defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
        mono_aot_register_jit_icall ("mono_amd64_start_gsharedvt_call", mono_amd64_start_gsharedvt_call);
 #endif
 
@@ -1906,6 +1865,7 @@ mono_arch_allocate_vars (MonoCompile *cfg)
                        cfg->ret->dreg = cinfo->ret.reg;
                        break;
                case ArgValuetypeAddrInIReg:
+               case ArgGsharedvtVariableInReg:
                        /* The register is volatile */
                        cfg->vret_addr->opcode = OP_REGOFFSET;
                        cfg->vret_addr->inst_basereg = cfg->frame_reg;
@@ -2083,7 +2043,7 @@ mono_arch_create_vars (MonoCompile *cfg)
                cfg->ret_var_is_local = TRUE;
 
        sig_ret = mini_get_underlying_type (sig->ret);
-       if (cinfo->ret.storage == ArgValuetypeAddrInIReg) {
+       if (cinfo->ret.storage == ArgValuetypeAddrInIReg || cinfo->ret.storage == ArgGsharedvtVariableInReg) {
                cfg->vret_addr = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_ARG);
                if (G_UNLIKELY (cfg->verbose_level > 1)) {
                        printf ("vret_addr = ");
@@ -2271,6 +2231,7 @@ mono_arch_get_llvm_call_info (MonoCompile *cfg, MonoMethodSignature *sig)
                break;
        }
        case ArgValuetypeAddrInIReg:
+       case ArgGsharedvtVariableInReg:
                /* Vtype returned using a hidden argument */
                linfo->ret.storage = LLVMArgVtypeRetAddr;
                linfo->vret_arg_index = cinfo->vret_arg_index;
@@ -2520,7 +2481,8 @@ mono_arch_emit_call (MonoCompile *cfg, MonoCallInst *call)
                        MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, ((MonoInst*)cfg->arch.vret_addr_loc)->dreg, call->vret_var->dreg);
                }
                break;
-       case ArgValuetypeAddrInIReg: {
+       case ArgValuetypeAddrInIReg:
+       case ArgGsharedvtVariableInReg: {
                MonoInst *vtarg;
                MONO_INST_NEW (cfg, vtarg, OP_MOVE);
                vtarg->sreg1 = call->vret_var->dreg;
@@ -2811,7 +2773,7 @@ mono_arch_start_dyn_call (MonoDynCallInfo *info, gpointer **args, guint8 *ret, g
                        pindex = 1;
        }
 
-       if (dinfo->cinfo->ret.storage == ArgValuetypeAddrInIReg)
+       if (dinfo->cinfo->ret.storage == ArgValuetypeAddrInIReg || dinfo->cinfo->ret.storage == ArgGsharedvtVariableInReg)
                p->regs [greg ++] = PTR_TO_GREG(ret);
 
        for (i = pindex; i < sig->param_count; i++) {
@@ -2992,7 +2954,7 @@ mono_arch_finish_dyn_call (MonoDynCallInfo *info, guint8 *buf)
                        /* Fall through */
                }
        case MONO_TYPE_VALUETYPE:
-               if (dinfo->cinfo->ret.storage == ArgValuetypeAddrInIReg) {
+               if (dinfo->cinfo->ret.storage == ArgValuetypeAddrInIReg || dinfo->cinfo->ret.storage == ArgGsharedvtVariableInReg) {
                        /* Nothing to do */
                } else {
                        ArgInfo *ainfo = &dinfo->cinfo->ret;
@@ -3926,21 +3888,6 @@ emit_setup_lmf (MonoCompile *cfg, guint8 *code, gint32 lmf_offset, int cfa_offse
        return code;
 }
 
-#define REAL_PRINT_REG(text,reg) \
-mono_assert (reg >= 0); \
-amd64_push_reg (code, AMD64_RAX); \
-amd64_push_reg (code, AMD64_RDX); \
-amd64_push_reg (code, AMD64_RCX); \
-amd64_push_reg (code, reg); \
-amd64_push_imm (code, reg); \
-amd64_push_imm (code, text " %d %p\n"); \
-amd64_mov_reg_imm (code, AMD64_RAX, printf); \
-amd64_call_reg (code, AMD64_RAX); \
-amd64_alu_reg_imm (code, X86_ADD, AMD64_RSP, 3*4); \
-amd64_pop_reg (code, AMD64_RCX); \
-amd64_pop_reg (code, AMD64_RDX); \
-amd64_pop_reg (code, AMD64_RAX);
-
 /* benchmark and set based on cpu */
 #define LOOP_ALIGNMENT 8
 #define bb_is_loop_start(bb) ((bb)->loop_body_start && (bb)->nesting)
@@ -8860,8 +8807,8 @@ mono_arch_opcode_supported (int opcode)
        }
 }
 
-#if defined(ENABLE_GSHAREDVT) && defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
-
-#include "../../../mono-extensions/mono/mini/mini-amd64-gsharedvt.c"
-
-#endif /* !ENABLE_GSHAREDVT */
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
+{
+       return get_call_info (mp, sig);
+}
index 343a42f8d99133d552f91face897c30d6e91dadf..1d04234c1785f7d5eb0045764bc3212a81cdfc42 100644 (file)
@@ -265,6 +265,51 @@ typedef struct {
        guint8 buffer [256];
 } DynCallArgs;
 
+typedef enum {
+       ArgInIReg,
+       ArgInFloatSSEReg,
+       ArgInDoubleSSEReg,
+       ArgOnStack,
+       ArgValuetypeInReg,
+       ArgValuetypeAddrInIReg,
+       /* gsharedvt argument passed by addr */
+       ArgGSharedVtInReg,
+       ArgGSharedVtOnStack,
+       /* Variable sized gsharedvt argument passed/returned by addr */
+       ArgGsharedvtVariableInReg,
+       ArgNone /* only in pair_storage */
+} ArgStorage;
+
+typedef struct {
+       gint16 offset;
+       gint8  reg;
+       ArgStorage storage : 8;
+
+       /* Only if storage == ArgValuetypeInReg */
+       ArgStorage pair_storage [2];
+       gint8 pair_regs [2];
+       /* The size of each pair (bytes) */
+       int pair_size [2];
+       int nregs;
+       /* Only if storage == ArgOnStack */
+       int arg_size; // Bytes, will always be rounded up/aligned to 8 byte boundary
+} ArgInfo;
+
+typedef struct {
+       int nargs;
+       guint32 stack_usage;
+       guint32 reg_usage;
+       guint32 freg_usage;
+       gboolean need_stack_align;
+       gboolean gsharedvt;
+       /* The index of the vret arg in the argument list */
+       int vret_arg_index;
+       ArgInfo ret;
+       ArgInfo sig_cookie;
+       ArgInfo args [1];
+} CallInfo;
+
+
 #define MONO_CONTEXT_SET_LLVM_EXC_REG(ctx, exc) do { (ctx)->gregs [AMD64_RAX] = (gsize)exc; } while (0)
 #define MONO_CONTEXT_SET_LLVM_EH_SELECTOR_REG(ctx, sel) do { (ctx)->gregs [AMD64_RDX] = (gsize)(sel); } while (0)
 
@@ -379,7 +424,6 @@ typedef struct {
 #define MONO_ARCH_HAVE_CONTEXT_SET_INT_REG 1
 #define MONO_ARCH_HAVE_SETUP_ASYNC_CALLBACK 1
 #define MONO_ARCH_HAVE_CREATE_LLVM_NATIVE_THUNK 1
-#define MONO_ARCH_GSHAREDVT_SUPPORTED 1
 #define MONO_ARCH_HAVE_OP_TAIL_CALL 1
 #define MONO_ARCH_HAVE_TRANSLATE_TLS_OFFSET 1
 #define MONO_ARCH_HAVE_DUMMY_INIT 1
@@ -395,6 +439,11 @@ typedef struct {
 #define MONO_ARCH_HAVE_TLS_GET_REG 1
 #endif
 
+#if !defined (TARGET_WIN32)
+#define MONO_ARCH_GSHAREDVT_SUPPORTED 1
+#endif
+
+
 #if defined(TARGET_APPLETVOS)
 /* No signals */
 #define MONO_ARCH_NEED_DIV_CHECK 1
@@ -460,5 +509,7 @@ void mono_arch_unwindinfo_install_unwind_info (gpointer* monoui, gpointer code,
 #define MONO_ARCH_HAVE_UNWIND_TABLE 1
 #endif
 
+CallInfo* mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig);
+
 #endif /* __MONO_MINI_AMD64_H__ */  
 
diff --git a/mono/mini/mini-arm-gsharedvt.c b/mono/mini/mini-arm-gsharedvt.c
new file mode 100644 (file)
index 0000000..aef522b
--- /dev/null
@@ -0,0 +1,329 @@
+/*
+ * mini-arm-gsharedvt.c: gsharedvt support code for arm
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <config.h>
+#include <glib.h>
+
+#include <mono/metadata/abi-details.h>
+#include <mono/metadata/appdomain.h>
+#include <mono/metadata/marshal.h>
+#include <mono/metadata/tabledefs.h>
+#include <mono/metadata/profiler-private.h>
+#include <mono/arch/arm/arm-codegen.h>
+#include <mono/arch/arm/arm-vfp-codegen.h>
+
+#include "mini.h"
+#include "mini-arm.h"
+
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+/*
+ * GSHAREDVT
+ */
+
+gboolean
+mono_arch_gsharedvt_sig_supported (MonoMethodSignature *sig)
+{
+       /*
+       if (sig->ret && is_variable_size (sig->ret))
+               return FALSE;
+       */
+       return TRUE;
+}
+
+static inline void
+add_to_map (GPtrArray *map, int src, int dst)
+{
+       g_ptr_array_add (map, GUINT_TO_POINTER (src));
+       g_ptr_array_add (map, GUINT_TO_POINTER (dst));
+}
+
+static inline int
+map_reg (int reg)
+{
+       return reg;
+}
+
+static inline int
+map_stack_slot (int slot)
+{
+       return slot + 4;
+}
+
+static int
+get_arg_slots (ArgInfo *ainfo, int **out_slots)
+{
+       int sreg = ainfo->reg;
+       int sslot = ainfo->offset / 4;
+       int *src = NULL;
+       int i, nsrc;
+
+       switch (ainfo->storage) {
+       case RegTypeGeneral:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_reg (sreg);
+               break;
+       case RegTypeIRegPair:
+               nsrc = 2;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_reg (sreg);
+               src [1] = map_reg (sreg + 1);
+               break;
+       case RegTypeStructByVal:
+               nsrc = ainfo->struct_size / 4;
+               src = g_malloc (nsrc * sizeof (int));
+               g_assert (ainfo->size <= nsrc);
+               for (i = 0; i < ainfo->size; ++i)
+                       src [i] = map_reg (sreg + i);
+               for (i = ainfo->size; i < nsrc; ++i)
+                       src [i] = map_stack_slot (sslot + (i - ainfo->size));
+               break;
+       case RegTypeBase:
+               nsrc = ainfo->size / 4;
+               src = g_malloc (nsrc * sizeof (int));
+               for (i = 0; i < nsrc; ++i)
+                       src [i] = map_stack_slot (sslot + i);
+               break;
+       case RegTypeBaseGen:
+               nsrc = 2;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_reg (ARMREG_R3);
+               src [1] = map_stack_slot (sslot);
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+
+       *out_slots = src;
+       return nsrc;
+}
+
+/*
+ * mono_arch_get_gsharedvt_call_info:
+ *
+ *   See mini-x86.c for documentation.
+ */
+gpointer
+mono_arch_get_gsharedvt_call_info (gpointer addr, MonoMethodSignature *normal_sig, MonoMethodSignature *gsharedvt_sig, gboolean gsharedvt_in, gint32 vcall_offset, gboolean calli)
+{
+       GSharedVtCallInfo *info;
+       CallInfo *caller_cinfo, *callee_cinfo;
+       MonoMethodSignature *caller_sig, *callee_sig;
+       int aindex, i;
+       gboolean var_ret = FALSE;
+       CallInfo *cinfo, *gcinfo;
+       MonoMethodSignature *sig, *gsig;
+       GPtrArray *map;
+
+       if (gsharedvt_in) {
+               caller_sig = normal_sig;
+               callee_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+       } else {
+               callee_sig = normal_sig;
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+               caller_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+       }
+
+       /*
+        * If GSHAREDVT_IN is true, this means we are transitioning from normal to gsharedvt code. The caller uses the
+        * normal call signature, while the callee uses the gsharedvt signature.
+        * If GSHAREDVT_IN is false, its the other way around.
+        */
+
+       /* sig/cinfo describes the normal call, while gsig/gcinfo describes the gsharedvt call */
+       if (gsharedvt_in) {
+               sig = caller_sig;
+               gsig = callee_sig;
+               cinfo = caller_cinfo;
+               gcinfo = callee_cinfo;
+       } else {
+               sig = callee_sig;
+               gsig = caller_sig;
+               cinfo = callee_cinfo;
+               gcinfo = caller_cinfo;
+       }
+
+       if (gcinfo->ret.storage == RegTypeStructByAddr && gsig->ret && mini_is_gsharedvt_type (gsig->ret)) {
+               /*
+                * The return type is gsharedvt
+                */
+               var_ret = TRUE;
+       }
+
+       /*
+        * The stack looks like this:
+        * <arguments>
+        * <ret addr>
+        * <saved ebp>
+        * <call area>
+        * We have to map the stack slots in <arguments> to the stack slots in <call area>.
+        * The argument registers are mapped to slot 0..3, stack slot 0 is mapped to slot 4, etc.
+        */
+       map = g_ptr_array_new ();
+
+       if (cinfo->ret.storage == RegTypeStructByAddr) {
+               /*
+                * Map ret arg.
+                * This handles the case when the method returns a normal vtype, and when it returns a type arg, and its instantiated
+                * with a vtype.
+                */
+               g_assert (caller_cinfo->ret.storage == RegTypeStructByAddr);
+               g_assert (callee_cinfo->ret.storage == RegTypeStructByAddr);
+               add_to_map (map, map_reg (caller_cinfo->ret.reg), map_reg (callee_cinfo->ret.reg));
+       }
+
+       for (aindex = 0; aindex < cinfo->nargs; ++aindex) {
+               ArgInfo *ainfo = &caller_cinfo->args [aindex];
+               ArgInfo *ainfo2 = &callee_cinfo->args [aindex];
+               int *src = NULL, *dst = NULL;
+               int nsrc, ndst, nslots, src_slot, arg_marshal;
+
+               /*
+                * The src descriptor looks like this:
+                * - 4 bits src slot
+                * - 12 bits number of slots
+                * - 8 bits marshal type (GSHAREDVT_ARG_...)
+                */
+
+               arg_marshal = GSHAREDVT_ARG_NONE;
+
+               if (ainfo->storage == RegTypeGSharedVtInReg || ainfo->storage == RegTypeGSharedVtOnStack) {
+                       /* Pass the value whose address is received in a reg by value */
+                       g_assert (ainfo2->storage != RegTypeGSharedVtInReg);
+                       ndst = get_arg_slots (ainfo2, &dst);
+                       nsrc = 1;
+                       src = g_new0 (int, 1);
+                       if (ainfo->storage == RegTypeGSharedVtInReg)
+                               src_slot = map_reg (ainfo->reg);
+                       else
+                               src_slot = map_stack_slot (ainfo->offset / 4);
+                       g_assert (ndst < 256);
+                       g_assert (src_slot < 16);
+                       src [0] = (ndst << 4) | src_slot;
+
+                       if (ainfo2->storage == RegTypeGeneral && ainfo2->size != 0 && ainfo2->size != 4) {
+                               /* Have to load less than 4 bytes */
+                               // FIXME: Signed types
+                               switch (ainfo2->size) {
+                               case 1:
+                                       arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL_U1;
+                                       break;
+                               case 2:
+                                       arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL_U2;
+                                       break;
+                               default:
+                                       g_assert_not_reached ();
+                                       break;
+                               }
+                       } else {
+                               arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL;
+                       }
+               } else {
+                       nsrc = get_arg_slots (ainfo, &src);
+               }
+               if (ainfo2->storage == RegTypeGSharedVtInReg) {
+                       /* Pass the address of the first src slot in a reg */
+                       arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF;
+                       ndst = 1;
+                       dst = g_new0 (int, 1);
+                       dst [0] = map_reg (ainfo2->reg);
+               } else if (ainfo2->storage == RegTypeGSharedVtOnStack) {
+                       /* Pass the address of the first src slot in a stack slot */
+                       arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF;
+                       ndst = 1;
+                       dst = g_new0 (int, 1);
+                       dst [0] = map_stack_slot (ainfo2->offset / 4);
+               } else {
+                       ndst = get_arg_slots (ainfo2, &dst);
+               }
+               if (nsrc)
+                       src [0] |= (arg_marshal << 16);
+               nslots = MIN (nsrc, ndst);
+
+               for (i = 0; i < nslots; ++i)
+                       add_to_map (map, src [i], dst [i]);
+
+               g_free (src);
+               g_free (dst);
+       }
+
+       info = mono_domain_alloc0 (mono_domain_get (), sizeof (GSharedVtCallInfo) + (map->len * sizeof (int)));
+       info->addr = addr;
+       info->stack_usage = callee_cinfo->stack_usage;
+       info->ret_marshal = GSHAREDVT_RET_NONE;
+       info->gsharedvt_in = gsharedvt_in ? 1 : 0;
+       info->vret_slot = -1;
+       info->calli = calli;
+       if (var_ret) {
+               g_assert (gcinfo->ret.storage == RegTypeStructByAddr);
+               info->vret_arg_reg = gcinfo->ret.reg;
+       } else {
+               info->vret_arg_reg = -1;
+       }
+       info->vcall_offset = vcall_offset;
+       info->map_count = map->len / 2;
+       for (i = 0; i < map->len; ++i)
+               info->map [i] = GPOINTER_TO_UINT (g_ptr_array_index (map, i));
+       g_ptr_array_free (map, TRUE);
+
+       /* Compute return value marshalling */
+       if (var_ret) {
+               switch (cinfo->ret.storage) {
+               case RegTypeGeneral:
+                       if (gsharedvt_in && !sig->ret->byref && sig->ret->type == MONO_TYPE_I1)
+                               info->ret_marshal = GSHAREDVT_RET_I1;
+                       else if (gsharedvt_in && !sig->ret->byref && (sig->ret->type == MONO_TYPE_U1 || sig->ret->type == MONO_TYPE_BOOLEAN))
+                               info->ret_marshal = GSHAREDVT_RET_U1;
+                       else if (gsharedvt_in && !sig->ret->byref && sig->ret->type == MONO_TYPE_I2)
+                               info->ret_marshal = GSHAREDVT_RET_I2;
+                       else if (gsharedvt_in && !sig->ret->byref && (sig->ret->type == MONO_TYPE_U2 || sig->ret->type == MONO_TYPE_CHAR))
+                               info->ret_marshal = GSHAREDVT_RET_U2;
+                       else
+                               info->ret_marshal = GSHAREDVT_RET_IREG;
+                       break;
+               case RegTypeIRegPair:
+                       info->ret_marshal = GSHAREDVT_RET_IREGS;
+                       break;
+               case RegTypeFP:
+                       // FIXME: VFP
+                       if (cinfo->ret.size == 4)
+                               info->ret_marshal = GSHAREDVT_RET_IREG;
+                       else
+                               info->ret_marshal = GSHAREDVT_RET_IREGS;
+                       break;
+               case RegTypeStructByAddr:
+                       info->ret_marshal = GSHAREDVT_RET_NONE;
+                       break;
+               default:
+                       g_assert_not_reached ();
+               }
+       }
+
+       if (gsharedvt_in && var_ret && caller_cinfo->ret.storage != RegTypeStructByAddr) {
+               /* Allocate stack space for the return value */
+               info->vret_slot = map_stack_slot (info->stack_usage / sizeof (gpointer));
+               info->stack_usage += mono_type_stack_size_internal (normal_sig->ret, NULL, FALSE) + sizeof (gpointer);
+       }
+
+       info->stack_usage = ALIGN_TO (info->stack_usage, MONO_ARCH_FRAME_ALIGNMENT);
+
+       g_free (caller_cinfo);
+       g_free (callee_cinfo);
+
+       return info;
+}
+
+#endif
\ No newline at end of file
index 63096e7439f6f435a68f47d3a0d7f3cc2c9c6fe5..c8fa1c9519b8a3cd82b81e7b38120ab20f2c0fbd 100644 (file)
@@ -2,6 +2,7 @@
  * mini-arm-tls.S: tls getters and setters for arm platforms
  *
  * Copyright 2015 Xamarin, Inc.
+        * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -129,7 +130,7 @@ DECLARE_GLOBAL_SYMBOL mono_fallback_set_tls_key
        .align 4
 DECLARE_GLOBAL_SYMBOL mono_fast_get_tls_key2
        bic     r0, r0, #0x80000000
-       mrc     15, 0, r1, cr13, cr0, #3
+       mrc     p15, 0, r1, cr13, cr0, #3
        lsls    r0, r0, #3
        ldr     r1, [r1, #4]
        add     r0, r1
@@ -145,7 +146,7 @@ DECLARE_GLOBAL_SYMBOL mono_fast_get_tls_key2_end
        .align 4
 DECLARE_GLOBAL_SYMBOL mono_fast_set_tls_key2
        bic     r0, r0, #0x80000000
-       mrc     15, 0, r2, cr13, cr0, #3
+       mrc     p15, 0, r2, cr13, cr0, #3
        lsls    r0, r0, #3
        ldr     r2, [r2, #4]
        add     r0, r2
index a85047f3873a62ed1c107d74e184b3b21bf867d1..86d4e123919cb97908c28153de6b512f1bc5d644 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2003 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "mini.h"
 #include <string.h>
@@ -903,7 +904,7 @@ mono_arch_init (void)
        mono_aot_register_jit_icall ("mono_arm_throw_exception", mono_arm_throw_exception);
        mono_aot_register_jit_icall ("mono_arm_throw_exception_by_token", mono_arm_throw_exception_by_token);
        mono_aot_register_jit_icall ("mono_arm_resume_unwind", mono_arm_resume_unwind);
-#if defined(ENABLE_GSHAREDVT)
+#if defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
        mono_aot_register_jit_icall ("mono_arm_start_gsharedvt_call", mono_arm_start_gsharedvt_call);
 #endif
        mono_aot_register_jit_icall ("mono_arm_unaligned_stack", mono_arm_unaligned_stack);
@@ -1159,50 +1160,6 @@ mono_arch_flush_icache (guint8 *code, gint size)
 #endif
 }
 
-typedef enum {
-       RegTypeNone,
-       /* Passed/returned in an ireg */
-       RegTypeGeneral,
-       /* Passed/returned in a pair of iregs */
-       RegTypeIRegPair,
-       /* Passed on the stack */
-       RegTypeBase,
-       /* First word in r3, second word on the stack */
-       RegTypeBaseGen,
-       /* FP value passed in either an ireg or a vfp reg */
-       RegTypeFP,
-       RegTypeStructByVal,
-       RegTypeStructByAddr,
-       /* gsharedvt argument passed by addr in greg */
-       RegTypeGSharedVtInReg,
-       /* gsharedvt argument passed by addr on stack */
-       RegTypeGSharedVtOnStack,
-       RegTypeHFA
-} ArgStorage;
-
-typedef struct {
-       gint32  offset;
-       guint16 vtsize; /* in param area */
-       /* RegTypeHFA */
-       int esize;
-       /* RegTypeHFA */
-       int nregs;
-       guint8  reg;
-       ArgStorage  storage;
-       gint32  struct_size;
-       guint8  size    : 4; /* 1, 2, 4, 8, or regs used by RegTypeStructByVal */
-} ArgInfo;
-
-typedef struct {
-       int nargs;
-       guint32 stack_usage;
-       /* The index of the vret arg in the argument list for RegTypeStructByAddr */
-       int vret_arg_index;
-       ArgInfo ret;
-       ArgInfo sig_cookie;
-       ArgInfo args [1];
-} CallInfo;
-
 #define DEBUG(a)
 
 static void inline
@@ -6575,7 +6532,7 @@ mono_arch_emit_prolog (MonoCompile *cfg)
                code = mono_arm_load_jumptable_entry_addr (code, jte, ARMREG_LR);
 #else
                ARM_MOV_REG_REG (code, ARMREG_LR, ARMREG_PC);
-               ARM_B (code, 2);
+               ARM_B (code, 1);
                *(gpointer*)code = &single_step_tramp;
                code += 4;
                *(gpointer*)code = breakpoint_tramp;
@@ -6827,7 +6784,7 @@ mono_arch_emit_exceptions (MonoCompile *cfg)
                        patch_info->ip.i = code - cfg->native_code;
                        ARM_BL (code, 0);
                        cfg->thunk_area += THUNK_SIZE;
-                       *(guint32*)(gpointer)code = exc_class->type_token;
+                       *(guint32*)(gpointer)code = exc_class->type_token - MONO_TOKEN_TYPE_DEF;
                        code += 4;
 #endif
                        break;
@@ -7664,8 +7621,8 @@ mono_arch_opcode_supported (int opcode)
        }
 }
 
-#if defined(ENABLE_GSHAREDVT)
-
-#include "../../../mono-extensions/mono/mini/mini-arm-gsharedvt.c"
-
-#endif /* !MONOTOUCH */
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
+{
+       return get_call_info (mp, sig);
+}
index b09db53452a1993fc7f13f51d056a678d1ef3a03..bcd922f522b628fac0f0fd7f0f91e13341022577 100644 (file)
@@ -1,5 +1,6 @@
 /*
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_MINI_ARM_H__
@@ -174,6 +175,51 @@ typedef struct {
        int map [MONO_ZERO_LEN_ARRAY];
 } GSharedVtCallInfo;
 
+
+typedef enum {
+       RegTypeNone,
+       /* Passed/returned in an ireg */
+       RegTypeGeneral,
+       /* Passed/returned in a pair of iregs */
+       RegTypeIRegPair,
+       /* Passed on the stack */
+       RegTypeBase,
+       /* First word in r3, second word on the stack */
+       RegTypeBaseGen,
+       /* FP value passed in either an ireg or a vfp reg */
+       RegTypeFP,
+       RegTypeStructByVal,
+       RegTypeStructByAddr,
+       /* gsharedvt argument passed by addr in greg */
+       RegTypeGSharedVtInReg,
+       /* gsharedvt argument passed by addr on stack */
+       RegTypeGSharedVtOnStack,
+       RegTypeHFA
+} ArgStorage;
+
+typedef struct {
+       gint32  offset;
+       guint16 vtsize; /* in param area */
+       /* RegTypeHFA */
+       int esize;
+       /* RegTypeHFA */
+       int nregs;
+       guint8  reg;
+       ArgStorage  storage;
+       gint32  struct_size;
+       guint8  size    : 4; /* 1, 2, 4, 8, or regs used by RegTypeStructByVal */
+} ArgInfo;
+
+typedef struct {
+       int nargs;
+       guint32 stack_usage;
+       /* The index of the vret arg in the argument list for RegTypeStructByAddr */
+       int vret_arg_index;
+       ArgInfo ret;
+       ArgInfo sig_cookie;
+       ArgInfo args [1];
+} CallInfo;
+
 /* Structure used by the sequence points in AOTed code */
 typedef struct {
        gpointer ss_trigger_page;
@@ -366,4 +412,7 @@ mono_arm_have_tls_get (void);
 void
 mono_arm_unaligned_stack (MonoMethod *method);
 
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig);
+
 #endif /* __MONO_MINI_ARM_H__ */
diff --git a/mono/mini/mini-arm64-gsharedvt.c b/mono/mini/mini-arm64-gsharedvt.c
new file mode 100644 (file)
index 0000000..df24c53
--- /dev/null
@@ -0,0 +1,418 @@
+/*
+ * mini-arm64-gsharedvt.c: gsharedvt support code for arm64
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include "mini.h"
+#include "mini-arm64.h"
+#include "mini-arm64-gsharedvt.h"
+
+/*
+ * GSHAREDVT
+ */
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+void
+mono_arm_gsharedvt_init (void)
+{
+       mono_aot_register_jit_icall ("mono_arm_start_gsharedvt_call", mono_arm_start_gsharedvt_call);
+}
+
+gboolean
+mono_arch_gsharedvt_sig_supported (MonoMethodSignature *sig)
+{
+       /*
+       if (sig->ret && is_variable_size (sig->ret))
+               return FALSE;
+       */
+       return TRUE;
+}
+
+static inline void
+add_to_map (GPtrArray *map, int src, int dst)
+{
+       g_ptr_array_add (map, GUINT_TO_POINTER (src));
+       g_ptr_array_add (map, GUINT_TO_POINTER (dst));
+}
+
+/*
+ * Slot mapping:
+ * 0..8  - r0..r8
+ * 9..16 - d0..d7
+ * 17..  - stack slots
+ */
+
+static inline int
+map_reg (int reg)
+{
+       return reg;
+}
+
+static inline int
+map_freg (int reg)
+{
+       return reg + NUM_GSHAREDVT_ARG_GREGS;
+}
+
+static inline int
+map_stack_slot (int slot)
+{
+       return slot + NUM_GSHAREDVT_ARG_GREGS + NUM_GSHAREDVT_ARG_FREGS;
+}
+
+static int
+get_arg_slots (ArgInfo *ainfo, int **out_slots)
+{
+       int sreg = ainfo->reg;
+       int sslot = ainfo->offset / 8;
+       int *src = NULL;
+       int i, nsrc;
+
+       switch (ainfo->storage) {
+       case ArgInIReg:
+       case ArgVtypeByRef:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_reg (sreg);
+               break;
+       case ArgVtypeByRefOnStack:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_stack_slot (sslot);
+               break;
+       case ArgInFReg:
+       case ArgInFRegR4:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_freg (sreg);
+               break;
+       case ArgHFA:
+               nsrc = ainfo->nregs;
+               src = g_malloc (nsrc * sizeof (int));
+               for (i = 0; i < ainfo->nregs; ++i)
+                       src [i] = map_freg (sreg + i);
+               break;
+       case ArgVtypeInIRegs:
+               nsrc = ainfo->nregs;
+               src = g_malloc (nsrc * sizeof (int));
+               for (i = 0; i < ainfo->nregs; ++i)
+                       src [i] = map_reg (sreg + i);
+               break;
+       case ArgOnStack:
+               nsrc = 1;
+               src = g_malloc (nsrc * sizeof (int));
+               src [0] = map_stack_slot (sslot);
+               break;
+       case ArgVtypeOnStack:
+               nsrc = ainfo->size / 8;
+               src = g_malloc (nsrc * sizeof (int));
+               for (i = 0; i < nsrc; ++i)
+                       src [i] = map_stack_slot (sslot + i);
+               break;
+       default:
+               NOT_IMPLEMENTED;
+               break;
+       }
+
+       *out_slots = src;
+       return nsrc;
+}
+
+/*
+ * mono_arch_get_gsharedvt_call_info:
+ *
+ *   See mini-x86.c for documentation.
+ */
+gpointer
+mono_arch_get_gsharedvt_call_info (gpointer addr, MonoMethodSignature *normal_sig, MonoMethodSignature *gsharedvt_sig, gboolean gsharedvt_in, gint32 vcall_offset, gboolean calli)
+{
+       GSharedVtCallInfo *info;
+       CallInfo *caller_cinfo, *callee_cinfo;
+       MonoMethodSignature *caller_sig, *callee_sig;
+       int aindex, i;
+       gboolean var_ret = FALSE;
+       CallInfo *cinfo, *gcinfo;
+       MonoMethodSignature *sig, *gsig;
+       GPtrArray *map;
+
+       if (gsharedvt_in) {
+               caller_sig = normal_sig;
+               callee_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+       } else {
+               callee_sig = normal_sig;
+               caller_sig = gsharedvt_sig;
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+       }
+
+       /*
+        * If GSHAREDVT_IN is true, this means we are transitioning from normal to gsharedvt code. The caller uses the
+        * normal call signature, while the callee uses the gsharedvt signature.
+        * If GSHAREDVT_IN is false, its the other way around.
+        */
+
+       /* sig/cinfo describes the normal call, while gsig/gcinfo describes the gsharedvt call */
+       if (gsharedvt_in) {
+               sig = caller_sig;
+               gsig = callee_sig;
+               cinfo = caller_cinfo;
+               gcinfo = callee_cinfo;
+       } else {
+               sig = callee_sig;
+               gsig = caller_sig;
+               cinfo = callee_cinfo;
+               gcinfo = caller_cinfo;
+       }
+
+       if (gcinfo->ret.gsharedvt) {
+               /*
+                * The return type is gsharedvt
+                */
+               var_ret = TRUE;
+       }
+
+       /*
+        * The stack looks like this:
+        * <arguments>
+        * <trampoline frame>
+        * <call area>
+        * We have to map the stack slots in <arguments> to the stack slots in <call area>.
+        */
+       map = g_ptr_array_new ();
+
+       for (aindex = 0; aindex < cinfo->nargs; ++aindex) {
+               ArgInfo *ainfo = &caller_cinfo->args [aindex];
+               ArgInfo *ainfo2 = &callee_cinfo->args [aindex];
+               int *src = NULL, *dst = NULL;
+               int nsrc, ndst, nslots, src_slot, arg_marshal;
+
+               /*
+                * The src descriptor looks like this:
+                * - 6 bits src slot
+                * - 12 bits number of slots
+                * - 4 bits marshal type (GSHAREDVT_ARG_...)
+                * - 4 bits size/sign descriptor (GSHAREDVT_ARG_SIZE)
+                * - 4 bits offset inside stack slots
+                */
+               arg_marshal = GSHAREDVT_ARG_NONE;
+
+               if (ainfo->gsharedvt) {
+                       /* Pass the value whose address is received in a reg by value */
+                       g_assert (!ainfo2->gsharedvt);
+                       ndst = get_arg_slots (ainfo2, &dst);
+                       nsrc = 1;
+                       src = g_new0 (int, 1);
+                       if (ainfo->storage == ArgVtypeByRef)
+                               src_slot = map_reg (ainfo->reg);
+                       else
+                               src_slot = map_stack_slot (ainfo->offset / 8);
+                       g_assert (ndst < 256);
+                       g_assert (src_slot < 64);
+                       src [0] = (ndst << 6) | src_slot;
+                       if (ainfo2->storage == ArgHFA && ainfo2->esize == 4)
+                               arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL_HFAR4;
+                       else if (ainfo2->storage == ArgVtypeByRef || ainfo2->storage == ArgVtypeByRefOnStack)
+                               arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYREF;
+                       else
+                               arg_marshal = GSHAREDVT_ARG_BYREF_TO_BYVAL;
+               } else {
+                       nsrc = get_arg_slots (ainfo, &src);
+               }
+               if (ainfo2->storage == ArgVtypeByRef && ainfo2->gsharedvt) {
+                       /* Pass the address of the first src slot in a reg */
+                       if (ainfo->storage != ArgVtypeByRef) {
+                               if (ainfo->storage == ArgHFA && ainfo->esize == 4) {
+                                       arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF_HFAR4;
+                                       g_assert (src [0] < 64);
+                                       g_assert (nsrc < 256);
+                                       src [0] |= (nsrc << 6);
+                               } else {
+                                       arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF;
+                               }
+                       }
+                       ndst = 1;
+                       dst = g_new0 (int, 1);
+                       dst [0] = map_reg (ainfo2->reg);
+               } else if (ainfo2->storage == ArgVtypeByRefOnStack && ainfo2->gsharedvt) {
+                       /* Pass the address of the first src slot in a stack slot */
+                       if (ainfo->storage != ArgVtypeByRef)
+                               arg_marshal = GSHAREDVT_ARG_BYVAL_TO_BYREF;
+                       ndst = 1;
+                       dst = g_new0 (int, 1);
+                       dst [0] = map_stack_slot (ainfo2->offset / 8);
+               } else {
+                       ndst = get_arg_slots (ainfo2, &dst);
+               }
+               if (nsrc)
+                       src [0] |= (arg_marshal << 18);
+               if (ainfo->storage == ArgOnStack && ainfo->slot_size != 8) {
+                       GSharedVtArgSize arg_size = GSHAREDVT_ARG_SIZE_NONE;
+
+                       /*
+                        * On IOS, stack arguments smaller than 8 bytes can
+                        * share a stack slot. Encode this information into
+                        * the descriptor.
+                        */
+                       switch (ainfo->slot_size) {
+                       case 1:
+                               arg_size = ainfo->sign ? GSHAREDVT_ARG_SIZE_I1 : GSHAREDVT_ARG_SIZE_U1;
+                               break;
+                       case 2:
+                               arg_size = ainfo->sign ? GSHAREDVT_ARG_SIZE_I2 : GSHAREDVT_ARG_SIZE_U2;
+                               break;
+                       case 4:
+                               arg_size = ainfo->sign ? GSHAREDVT_ARG_SIZE_I4 : GSHAREDVT_ARG_SIZE_U4;
+                               break;
+                       default:
+                               NOT_IMPLEMENTED;
+                               break;
+                       }
+                       /* Encode the size/sign */
+                       src [0] |= (arg_size << 22);
+                       /* Encode the offset inside the stack slot */
+                       src [0] |= ((ainfo->offset % 8) << 26);
+                       if (ainfo2->storage == ArgOnStack)
+                               dst [0] |= ((ainfo2->offset % 8) << 26);
+               } else if (ainfo2->storage == ArgOnStack && ainfo2->slot_size != 8) {
+                       /* The caller passes in an address, need to store it into a stack slot */
+
+                       GSharedVtArgSize arg_size = GSHAREDVT_ARG_SIZE_NONE;
+                       switch (ainfo2->slot_size) {
+                       case 1:
+                               arg_size = ainfo2->sign ? GSHAREDVT_ARG_SIZE_I1 : GSHAREDVT_ARG_SIZE_U1;
+                               break;
+                       case 2:
+                               arg_size = ainfo2->sign ? GSHAREDVT_ARG_SIZE_I2 : GSHAREDVT_ARG_SIZE_U2;
+                               break;
+                       case 4:
+                               arg_size = ainfo2->sign ? GSHAREDVT_ARG_SIZE_I4 : GSHAREDVT_ARG_SIZE_U4;
+                               break;
+                       default:
+                               NOT_IMPLEMENTED;
+                               break;
+                       }
+                       /* Encode the size/sign */
+                       src [0] |= (arg_size << 22);
+                       /* Encode the offset inside the stack slot */
+                       dst [0] |= ((ainfo2->offset % 8) << 26);
+               }
+               nslots = MIN (nsrc, ndst);
+
+               for (i = 0; i < nslots; ++i)
+                       add_to_map (map, src [i], dst [i]);
+
+               g_free (src);
+               g_free (dst);
+       }
+
+       if (cinfo->ret.storage == ArgVtypeByRef) {
+               /* Both the caller and the callee pass the vtype ret address in r8 */
+               g_assert (cinfo->ret.storage == gcinfo->ret.storage);
+               add_to_map (map, map_reg (ARMREG_R8), map_reg (ARMREG_R8));
+       }
+
+       info = mono_domain_alloc0 (mono_domain_get (), sizeof (GSharedVtCallInfo) + (map->len * sizeof (int)));
+       info->addr = addr;
+       info->stack_usage = callee_cinfo->stack_usage;
+       info->ret_marshal = GSHAREDVT_RET_NONE;
+       info->gsharedvt_in = gsharedvt_in ? 1 : 0;
+       info->vret_slot = -1;
+       info->calli = calli;
+
+       if (var_ret) {
+               g_assert (gcinfo->ret.gsharedvt);
+               info->vret_arg_reg = map_reg (ARMREG_R8);
+       } else {
+               info->vret_arg_reg = -1;
+       }
+
+       info->vcall_offset = vcall_offset;
+       info->map_count = map->len / 2;
+       for (i = 0; i < map->len; ++i)
+               info->map [i] = GPOINTER_TO_UINT (g_ptr_array_index (map, i));
+       g_ptr_array_free (map, TRUE);
+
+       /* Compute return value marshalling */
+       if (var_ret) {
+               switch (cinfo->ret.storage) {
+               case ArgInIReg:
+                       if (!gsharedvt_in || sig->ret->byref) {
+                               info->ret_marshal = GSHAREDVT_RET_I8;
+                       } else {
+                               switch (sig->ret->type) {
+                               case MONO_TYPE_I1:
+                                       info->ret_marshal = GSHAREDVT_RET_I1;
+                                       break;
+                               case MONO_TYPE_U1:
+                               case MONO_TYPE_BOOLEAN:
+                                       info->ret_marshal = GSHAREDVT_RET_U1;
+                                       break;
+                               case MONO_TYPE_I2:
+                                       info->ret_marshal = GSHAREDVT_RET_I2;
+                                       break;
+                               case MONO_TYPE_U2:
+                               case MONO_TYPE_CHAR:
+                                       info->ret_marshal = GSHAREDVT_RET_U2;
+                                       break;
+                               case MONO_TYPE_I4:
+                                       info->ret_marshal = GSHAREDVT_RET_I4;
+                                       break;
+                               case MONO_TYPE_U4:
+                                       info->ret_marshal = GSHAREDVT_RET_U4;
+                                       break;
+                               default:
+                                       info->ret_marshal = GSHAREDVT_RET_I8;
+                                       break;
+                               }
+                       }
+                       break;
+               case ArgInFReg:
+                       info->ret_marshal = GSHAREDVT_RET_R8;
+                       break;
+               case ArgInFRegR4:
+                       info->ret_marshal = GSHAREDVT_RET_R4;
+                       break;
+               case ArgVtypeInIRegs:
+                       info->ret_marshal = GSHAREDVT_RET_IREGS_1 - 1 + cinfo->ret.nregs;
+                       break;
+               case ArgHFA:
+                       if (cinfo->ret.esize == 4)
+                               info->ret_marshal = GSHAREDVT_RET_HFAR4_1 - 1 + cinfo->ret.nregs;
+                       else
+                               info->ret_marshal = GSHAREDVT_RET_HFAR8_1 - 1 + cinfo->ret.nregs;
+                       break;
+               case ArgVtypeByRef:
+                       /* No conversion needed */
+                       break;
+               default:
+                       g_assert_not_reached ();
+               }
+       }
+
+       if (gsharedvt_in && var_ret && cinfo->ret.storage != ArgVtypeByRef) {
+               /* Allocate stack space for the return value */
+               info->vret_slot = map_stack_slot (info->stack_usage / sizeof (gpointer));
+               info->stack_usage += mono_type_stack_size_internal (normal_sig->ret, NULL, FALSE) + sizeof (gpointer);
+       }
+
+       info->stack_usage = ALIGN_TO (info->stack_usage, MONO_ARCH_FRAME_ALIGNMENT);
+
+       return info;
+}
+
+#else
+
+void
+mono_arm_gsharedvt_init (void)
+{
+}
+
+#endif /* MONO_ARCH_GSHAREDVT_SUPPORTED */
diff --git a/mono/mini/mini-arm64-gsharedvt.h b/mono/mini/mini-arm64-gsharedvt.h
new file mode 100644 (file)
index 0000000..b828218
--- /dev/null
@@ -0,0 +1,84 @@
+#ifndef __MINI_ARM64_GSHAREDVT_H__
+#define __MINI_ARM64_GSHAREDVT_H__
+
+/* Argument marshallings for calls between gsharedvt and normal code */
+typedef enum {
+       GSHAREDVT_ARG_NONE = 0,
+       GSHAREDVT_ARG_BYVAL_TO_BYREF = 1,
+       GSHAREDVT_ARG_BYVAL_TO_BYREF_HFAR4 = 2,
+       GSHAREDVT_ARG_BYREF_TO_BYVAL = 3,
+       GSHAREDVT_ARG_BYREF_TO_BYVAL_HFAR4 = 4,
+       GSHAREDVT_ARG_BYREF_TO_BYREF = 5
+} GSharedVtArgMarshal;
+
+/* For arguments passed on the stack on ios */
+typedef enum {
+       GSHAREDVT_ARG_SIZE_NONE = 0,
+       GSHAREDVT_ARG_SIZE_I1 = 1,
+       GSHAREDVT_ARG_SIZE_U1 = 2,
+       GSHAREDVT_ARG_SIZE_I2 = 3,
+       GSHAREDVT_ARG_SIZE_U2 = 4,
+       GSHAREDVT_ARG_SIZE_I4 = 5,
+       GSHAREDVT_ARG_SIZE_U4 = 6,
+} GSharedVtArgSize;
+
+/* Return value marshalling for calls between gsharedvt and normal code */
+typedef enum {
+       GSHAREDVT_RET_NONE = 0,
+       GSHAREDVT_RET_I8 = 1,
+       GSHAREDVT_RET_I1 = 2,
+       GSHAREDVT_RET_U1 = 3,
+       GSHAREDVT_RET_I2 = 4,
+       GSHAREDVT_RET_U2 = 5,
+       GSHAREDVT_RET_I4 = 6,
+       GSHAREDVT_RET_U4 = 7,
+       GSHAREDVT_RET_R8 = 8,
+       GSHAREDVT_RET_R4 = 9,
+       GSHAREDVT_RET_IREGS_1 = 10,
+       GSHAREDVT_RET_IREGS_2 = 11,
+       GSHAREDVT_RET_IREGS_3 = 12,
+       GSHAREDVT_RET_IREGS_4 = 13,
+       GSHAREDVT_RET_IREGS_5 = 14,
+       GSHAREDVT_RET_IREGS_6 = 15,
+       GSHAREDVT_RET_IREGS_7 = 16,
+       GSHAREDVT_RET_IREGS_8 = 17,
+       GSHAREDVT_RET_HFAR8_1 = 18,
+       GSHAREDVT_RET_HFAR8_2 = 19,
+       GSHAREDVT_RET_HFAR8_3 = 20,
+       GSHAREDVT_RET_HFAR8_4 = 21,
+       GSHAREDVT_RET_HFAR4_1 = 22,
+       GSHAREDVT_RET_HFAR4_2 = 23,
+       GSHAREDVT_RET_HFAR4_3 = 24,
+       GSHAREDVT_RET_HFAR4_4 = 25,
+       GSHAREDVT_RET_NUM = 26
+} GSharedVtRetMarshal;
+
+typedef struct {
+       /* Method address to call */
+       gpointer addr;
+       /* The trampoline reads this, so keep the size explicit */
+       int ret_marshal;
+       /* If ret_marshal != NONE, this is the reg of the vret arg, else -1 */
+       /* Equivalent of vret_arg_slot in x86 implementation. */
+       int vret_arg_reg;
+       /* The stack slot where the return value will be stored */
+       int vret_slot;
+       int stack_usage, map_count;
+       /* If not -1, then make a virtual call using this vtable offset */
+       int vcall_offset;
+       /* If 1, make an indirect call to the address in the rgctx reg */
+       int calli;
+       /* Whenever this is a in or an out call */
+       int gsharedvt_in;
+       /* Maps stack slots/registers in the caller to the stack slots/registers in the callee */
+       int map [MONO_ZERO_LEN_ARRAY];
+} GSharedVtCallInfo;
+
+/* Number of argument registers (r0..r8) */
+#define NUM_GSHAREDVT_ARG_GREGS 9
+#define NUM_GSHAREDVT_ARG_FREGS 8
+
+gpointer
+mono_arm_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg);
+
+#endif /* __MINI_ARM64_GSHAREDVT_H__ */
index 517f6c68a9dd5b3ff95373c721f84ecd57f1f994..cb75bdf7a74fda7899a813f97ceae60ad6f7c895 100644 (file)
@@ -1 +1,5237 @@
-#include "../../../mono-extensions/mono/mini/mini-arm64.c"
+/*
+ * mini-arm64.c: ARM64 backend for the Mono code generator
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * 
+ * Based on mini-arm.c:
+ *
+ * Authors:
+ *   Paolo Molaro (lupus@ximian.com)
+ *   Dietmar Maurer (dietmar@ximian.com)
+ *
+ * (C) 2003 Ximian, Inc.
+ * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
+ * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+#include "mini.h"
+#include "cpu-arm64.h"
+#include "ir-emit.h"
+
+#include <mono/arch/arm64/arm64-codegen.h>
+#include <mono/utils/mono-mmap.h>
+#include <mono/utils/mono-memory-model.h>
+#include <mono/metadata/abi-details.h>
+
+/*
+ * Documentation:
+ *
+ * - ARM(R) Architecture Reference Manual, ARMv8, for ARMv8-A architecture profile (DDI0487A_a_armv8_arm.pdf)
+ * - Procedure Call Standard for the ARM 64-bit Architecture (AArch64) (IHI0055B_aapcs64.pdf)
+ * - ELF for the ARM 64-bit Architecture (IHI0056B_aaelf64.pdf)
+ *
+ * Register usage:
+ * - ip0/ip1/lr are used as temporary registers
+ * - r27 is used as the rgctx/imt register
+ * - r28 is used to access arguments passed on the stack
+ * - d15/d16 are used as fp temporary registers
+ */
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+#define FP_TEMP_REG ARMREG_D16
+#define FP_TEMP_REG2 ARMREG_D17
+
+#define THUNK_SIZE (4 * 4)
+
+/* The single step trampoline */
+static gpointer ss_trampoline;
+
+/* The breakpoint trampoline */
+static gpointer bp_trampoline;
+
+static gboolean ios_abi;
+
+static __attribute__((warn_unused_result)) guint8* emit_load_regset (guint8 *code, guint64 regs, int basereg, int offset);
+
+const char*
+mono_arch_regname (int reg)
+{
+       static const char * rnames[] = {
+               "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9",
+               "r10", "r11", "r12", "r13", "r14", "r15", "r16", "r17", "r18", "r19",
+               "r20", "r21", "r22", "r23", "r24", "r25", "r26", "r27", "r28", "fp",
+               "lr", "sp"
+       };
+       if (reg >= 0 && reg < 32)
+               return rnames [reg];
+       return "unknown";
+}
+
+const char*
+mono_arch_fregname (int reg)
+{
+       static const char * rnames[] = {
+               "d0", "d1", "d2", "d3", "d4", "d5", "d6", "d7", "d8", "d9",
+               "d10", "d11", "d12", "d13", "d14", "d15", "d16", "d17", "d18", "d19",
+               "d20", "d21", "d22", "d23", "d24", "d25", "d26", "d27", "d28", "d29",
+               "d30", "d31"
+       };
+       if (reg >= 0 && reg < 32)
+               return rnames [reg];
+       return "unknown fp";
+}
+
+int
+mono_arch_get_argument_info (MonoMethodSignature *csig, int param_count, MonoJitArgumentInfo *arg_info)
+{
+       NOT_IMPLEMENTED;
+       return 0;
+}
+
+#define MAX_ARCH_DELEGATE_PARAMS 7
+
+static gpointer
+get_delegate_invoke_impl (gboolean has_target, gboolean param_count, guint32 *code_size)
+{
+       guint8 *code, *start;
+
+       if (has_target) {
+               start = code = mono_global_codeman_reserve (12);
+
+               /* Replace the this argument with the target */
+               arm_ldrx (code, ARMREG_IP0, ARMREG_R0, MONO_STRUCT_OFFSET (MonoDelegate, method_ptr));
+               arm_ldrx (code, ARMREG_R0, ARMREG_R0, MONO_STRUCT_OFFSET (MonoDelegate, target));
+               arm_brx (code, ARMREG_IP0);
+
+               g_assert ((code - start) <= 12);
+
+               mono_arch_flush_icache (start, 12);
+       } else {
+               int size, i;
+
+               size = 8 + param_count * 4;
+               start = code = mono_global_codeman_reserve (size);
+
+               arm_ldrx (code, ARMREG_IP0, ARMREG_R0, MONO_STRUCT_OFFSET (MonoDelegate, method_ptr));
+               /* slide down the arguments */
+               for (i = 0; i < param_count; ++i)
+                       arm_movx (code, i, i + 1);
+               arm_brx (code, ARMREG_IP0);
+
+               g_assert ((code - start) <= size);
+
+               mono_arch_flush_icache (start, size);
+       }
+
+       if (code_size)
+               *code_size = code - start;
+
+       return start;
+}
+
+/*
+ * mono_arch_get_delegate_invoke_impls:
+ *
+ *   Return a list of MonoAotTrampInfo structures for the delegate invoke impl
+ * trampolines.
+ */
+GSList*
+mono_arch_get_delegate_invoke_impls (void)
+{
+       GSList *res = NULL;
+       guint8 *code;
+       guint32 code_len;
+       int i;
+       char *tramp_name;
+
+       code = get_delegate_invoke_impl (TRUE, 0, &code_len);
+       res = g_slist_prepend (res, mono_tramp_info_create ("delegate_invoke_impl_has_target", code, code_len, NULL, NULL));
+
+       for (i = 0; i <= MAX_ARCH_DELEGATE_PARAMS; ++i) {
+               code = get_delegate_invoke_impl (FALSE, i, &code_len);
+               tramp_name = g_strdup_printf ("delegate_invoke_impl_target_%d", i);
+               res = g_slist_prepend (res, mono_tramp_info_create (tramp_name, code, code_len, NULL, NULL));
+               g_free (tramp_name);
+       }
+
+       return res;
+}
+
+gpointer
+mono_arch_get_delegate_invoke_impl (MonoMethodSignature *sig, gboolean has_target)
+{
+       guint8 *code, *start;
+
+       /*
+        * vtypes are returned in registers, or using the dedicated r8 register, so
+        * they can be supported by delegate invokes.
+        */
+
+       if (has_target) {
+               static guint8* cached = NULL;
+
+               if (cached)
+                       return cached;
+
+               if (mono_aot_only)
+                       start = mono_aot_get_trampoline ("delegate_invoke_impl_has_target");
+               else
+                       start = get_delegate_invoke_impl (TRUE, 0, NULL);
+               mono_memory_barrier ();
+               cached = start;
+               return cached;
+       } else {
+               static guint8* cache [MAX_ARCH_DELEGATE_PARAMS + 1] = {NULL};
+               int i;
+
+               if (sig->param_count > MAX_ARCH_DELEGATE_PARAMS)
+                       return NULL;
+               for (i = 0; i < sig->param_count; ++i)
+                       if (!mono_is_regsize_var (sig->params [i]))
+                               return NULL;
+
+               code = cache [sig->param_count];
+               if (code)
+                       return code;
+
+               if (mono_aot_only) {
+                       char *name = g_strdup_printf ("delegate_invoke_impl_target_%d", sig->param_count);
+                       start = mono_aot_get_trampoline (name);
+                       g_free (name);
+               } else {
+                       start = get_delegate_invoke_impl (FALSE, sig->param_count, NULL);
+               }
+               mono_memory_barrier ();
+               cache [sig->param_count] = start;
+               return start;
+       }
+
+       return NULL;
+}
+
+gpointer
+mono_arch_get_delegate_virtual_invoke_impl (MonoMethodSignature *sig, MonoMethod *method, int offset, gboolean load_imt_reg)
+{
+       return NULL;
+}
+
+gpointer
+mono_arch_get_this_arg_from_call (mgreg_t *regs, guint8 *code)
+{
+       return (gpointer)regs [ARMREG_R0];
+}
+
+void
+mono_arch_cpu_init (void)
+{
+}
+
+void
+mono_arch_init (void)
+{
+       mono_aot_register_jit_icall ("mono_arm_throw_exception", mono_arm_throw_exception);
+       mono_aot_register_jit_icall ("mono_arm_resume_unwind", mono_arm_resume_unwind);
+
+       if (!mono_aot_only)
+               bp_trampoline = mini_get_breakpoint_trampoline ();
+
+       mono_arm_gsharedvt_init ();
+
+#if defined(TARGET_IOS)
+       ios_abi = TRUE;
+#endif
+}
+
+void
+mono_arch_cleanup (void)
+{
+}
+
+guint32
+mono_arch_cpu_optimizations (guint32 *exclude_mask)
+{
+       *exclude_mask = 0;
+       return 0;
+}
+
+guint32
+mono_arch_cpu_enumerate_simd_versions (void)
+{
+       return 0;
+}
+
+void
+mono_arch_register_lowlevel_calls (void)
+{
+}
+
+void
+mono_arch_finish_init (void)
+{
+}
+
+/* The maximum length is 2 instructions */
+static guint8*
+emit_imm (guint8 *code, int dreg, int imm)
+{
+       // FIXME: Optimize this
+       if (imm < 0) {
+               gint64 limm = imm;
+               arm_movnx (code, dreg, (~limm) & 0xffff, 0);
+               arm_movkx (code, dreg, (limm >> 16) & 0xffff, 16);
+       } else {
+               arm_movzx (code, dreg, imm & 0xffff, 0);
+               if (imm >> 16)
+                       arm_movkx (code, dreg, (imm >> 16) & 0xffff, 16);
+       }
+
+       return code;
+}
+
+/* The maximum length is 4 instructions */
+static guint8*
+emit_imm64 (guint8 *code, int dreg, guint64 imm)
+{
+       // FIXME: Optimize this
+       arm_movzx (code, dreg, imm & 0xffff, 0);
+       if ((imm >> 16) & 0xffff)
+               arm_movkx (code, dreg, (imm >> 16) & 0xffff, 16);
+       if ((imm >> 32) & 0xffff)
+               arm_movkx (code, dreg, (imm >> 32) & 0xffff, 32);
+       if ((imm >> 48) & 0xffff)
+               arm_movkx (code, dreg, (imm >> 48) & 0xffff, 48);
+
+       return code;
+}
+
+guint8*
+mono_arm_emit_imm64 (guint8 *code, int dreg, gint64 imm)
+{
+       return emit_imm64 (code, dreg, imm);
+}
+
+/*
+ * emit_imm_template:
+ *
+ *   Emit a patchable code sequence for constructing a 64 bit immediate.
+ */
+static guint8*
+emit_imm64_template (guint8 *code, int dreg)
+{
+       arm_movzx (code, dreg, 0, 0);
+       arm_movkx (code, dreg, 0, 16);
+       arm_movkx (code, dreg, 0, 32);
+       arm_movkx (code, dreg, 0, 48);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_addw_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       if (!arm_is_arith_imm (imm)) {
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_addw (code, dreg, sreg, ARMREG_LR);
+       } else {
+               arm_addw_imm (code, dreg, sreg, imm);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_addx_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       if (!arm_is_arith_imm (imm)) {
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_addx (code, dreg, sreg, ARMREG_LR);
+       } else {
+               arm_addx_imm (code, dreg, sreg, imm);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_subw_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       if (!arm_is_arith_imm (imm)) {
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_subw (code, dreg, sreg, ARMREG_LR);
+       } else {
+               arm_subw_imm (code, dreg, sreg, imm);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_subx_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       if (!arm_is_arith_imm (imm)) {
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_subx (code, dreg, sreg, ARMREG_LR);
+       } else {
+               arm_subx_imm (code, dreg, sreg, imm);
+       }
+       return code;
+}
+
+/* Emit sp+=imm. Clobbers ip0/ip1 */
+static inline __attribute__((warn_unused_result)) guint8*
+emit_addx_sp_imm (guint8 *code, int imm)
+{
+       code = emit_imm (code, ARMREG_IP0, imm);
+       arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+       arm_addx (code, ARMREG_IP1, ARMREG_IP1, ARMREG_IP0);
+       arm_movspx (code, ARMREG_SP, ARMREG_IP1);
+       return code;
+}
+
+/* Emit sp-=imm. Clobbers ip0/ip1 */
+static inline __attribute__((warn_unused_result)) guint8*
+emit_subx_sp_imm (guint8 *code, int imm)
+{
+       code = emit_imm (code, ARMREG_IP0, imm);
+       arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+       arm_subx (code, ARMREG_IP1, ARMREG_IP1, ARMREG_IP0);
+       arm_movspx (code, ARMREG_SP, ARMREG_IP1);
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_andw_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_andw (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_andx_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_andx (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_orrw_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_orrw (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_orrx_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_orrx (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_eorw_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_eorw (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_eorx_imm (guint8 *code, int dreg, int sreg, int imm)
+{
+       // FIXME:
+       code = emit_imm (code, ARMREG_LR, imm);
+       arm_eorx (code, dreg, sreg, ARMREG_LR);
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_cmpw_imm (guint8 *code, int sreg, int imm)
+{
+       if (imm == 0) {
+               arm_cmpw (code, sreg, ARMREG_RZR);
+       } else {
+               // FIXME:
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_cmpw (code, sreg, ARMREG_LR);
+       }
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_cmpx_imm (guint8 *code, int sreg, int imm)
+{
+       if (imm == 0) {
+               arm_cmpx (code, sreg, ARMREG_RZR);
+       } else {
+               // FIXME:
+               code = emit_imm (code, ARMREG_LR, imm);
+               arm_cmpx (code, sreg, ARMREG_LR);
+       }
+
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strb (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strb_imm (imm)) {
+               arm_strb (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_strb_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strh (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strh_imm (imm)) {
+               arm_strh (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_strh_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strw (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strw_imm (imm)) {
+               arm_strw (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_strw_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strfpw (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strw_imm (imm)) {
+               arm_strfpw (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_addx (code, ARMREG_IP0, rn, ARMREG_IP0);
+               arm_strfpw (code, rt, ARMREG_IP0, 0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strfpx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strx_imm (imm)) {
+               arm_strfpx (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_addx (code, ARMREG_IP0, rn, ARMREG_IP0);
+               arm_strfpx (code, rt, ARMREG_IP0, 0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_strx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_strx_imm (imm)) {
+               arm_strx (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_strx_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrb (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 1)) {
+               arm_ldrb (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrb_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrsbx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 1)) {
+               arm_ldrsbx (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrsbx_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrh (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 2)) {
+               arm_ldrh (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrh_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrshx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 2)) {
+               arm_ldrshx (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrshx_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrswx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 4)) {
+               arm_ldrswx (code, rt, rn, imm);
+       } else {
+               g_assert (rt != ARMREG_IP0);
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrswx_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrw (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 4)) {
+               arm_ldrw (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrw_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 8)) {
+               arm_ldrx (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_ldrx_reg (code, rt, rn, ARMREG_IP0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrfpw (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 4)) {
+               arm_ldrfpw (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_addx (code, ARMREG_IP0, rn, ARMREG_IP0);
+               arm_ldrfpw (code, rt, ARMREG_IP0, 0);
+       }
+       return code;
+}
+
+static inline __attribute__((warn_unused_result)) guint8*
+emit_ldrfpx (guint8 *code, int rt, int rn, int imm)
+{
+       if (arm_is_pimm12_scaled (imm, 8)) {
+               arm_ldrfpx (code, rt, rn, imm);
+       } else {
+               g_assert (rn != ARMREG_IP0);
+               code = emit_imm (code, ARMREG_IP0, imm);
+               arm_addx (code, ARMREG_IP0, rn, ARMREG_IP0);
+               arm_ldrfpx (code, rt, ARMREG_IP0, 0);
+       }
+       return code;
+}
+
+guint8*
+mono_arm_emit_ldrx (guint8 *code, int rt, int rn, int imm)
+{
+       return emit_ldrx (code, rt, rn, imm);
+}
+
+static guint8*
+emit_call (MonoCompile *cfg, guint8* code, guint32 patch_type, gconstpointer data)
+{
+       /*
+       mono_add_patch_info_rel (cfg, code - cfg->native_code, patch_type, data, MONO_R_ARM64_IMM);
+       code = emit_imm64_template (code, ARMREG_LR);
+       arm_blrx (code, ARMREG_LR);
+       */
+       mono_add_patch_info_rel (cfg, code - cfg->native_code, patch_type, data, MONO_R_ARM64_BL);
+       arm_bl (code, code);
+       cfg->thunk_area += THUNK_SIZE;
+       return code;
+}
+
+static guint8*
+emit_aotconst_full (MonoCompile *cfg, MonoJumpInfo **ji, guint8 *code, guint8 *start, int dreg, guint32 patch_type, gconstpointer data)
+{
+       if (cfg)
+               mono_add_patch_info (cfg, code - cfg->native_code, patch_type, data);
+       else
+               *ji = mono_patch_info_list_prepend (*ji, code - start, patch_type, data);
+       /* See arch_emit_got_access () in aot-compiler.c */
+       arm_ldrx_lit (code, dreg, 0);
+       arm_nop (code);
+       arm_nop (code);
+       return code;
+}
+
+static guint8*
+emit_aotconst (MonoCompile *cfg, guint8 *code, int dreg, guint32 patch_type, gconstpointer data)
+{
+       return emit_aotconst_full (cfg, NULL, code, NULL, dreg, patch_type, data);
+}
+
+/*
+ * mono_arm_emit_aotconst:
+ *
+ *   Emit code to load an AOT constant into DREG. Usable from trampolines.
+ */
+guint8*
+mono_arm_emit_aotconst (gpointer ji, guint8 *code, guint8 *code_start, int dreg, guint32 patch_type, gconstpointer data)
+{
+       return emit_aotconst_full (NULL, (MonoJumpInfo**)ji, code, code_start, dreg, patch_type, data);
+}
+
+static guint8*
+emit_tls_get (guint8 *code, int dreg, int tls_offset)
+{
+       arm_mrs (code, dreg, ARM_MRS_REG_TPIDR_EL0);
+       if (tls_offset < 256) {
+               arm_ldrx (code, dreg, dreg, tls_offset);
+       } else {
+               code = emit_addx_imm (code, dreg, dreg, tls_offset);
+               arm_ldrx (code, dreg, dreg, 0);
+       }
+       return code;
+}
+
+static guint8*
+emit_tls_get_reg (guint8 *code, int dreg, int offset_reg)
+{
+       g_assert (offset_reg != ARMREG_IP0);
+       arm_mrs (code, ARMREG_IP0, ARM_MRS_REG_TPIDR_EL0);
+       arm_ldrx_reg (code, dreg, ARMREG_IP0, offset_reg);
+       return code;
+}
+
+static guint8*
+emit_tls_set (guint8 *code, int sreg, int tls_offset)
+{
+       int tmpreg = ARMREG_IP0;
+
+       g_assert (sreg != tmpreg);
+       arm_mrs (code, tmpreg, ARM_MRS_REG_TPIDR_EL0);
+       if (tls_offset < 256) {
+               arm_strx (code, sreg, tmpreg, tls_offset);
+       } else {
+               code = emit_addx_imm (code, tmpreg, tmpreg, tls_offset);
+               arm_strx (code, sreg, tmpreg, 0);
+       }
+       return code;
+}
+
+
+static guint8*
+emit_tls_set_reg (guint8 *code, int sreg, int offset_reg)
+{
+       int tmpreg = ARMREG_IP0;
+
+       g_assert (sreg != tmpreg);
+       arm_mrs (code, tmpreg, ARM_MRS_REG_TPIDR_EL0);
+       arm_strx_reg (code, sreg, tmpreg, offset_reg);
+       return code;
+}
+
+/*
+ * Emits
+ * - mov sp, fp
+ * - ldrp [fp, lr], [sp], !stack_offfset
+ * Clobbers TEMP_REGS.
+ */
+__attribute__((warn_unused_result)) guint8*
+mono_arm_emit_destroy_frame (guint8 *code, int stack_offset, guint64 temp_regs)
+{
+       arm_movspx (code, ARMREG_SP, ARMREG_FP);
+
+       if (arm_is_ldpx_imm (stack_offset)) {
+               arm_ldpx_post (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, stack_offset);
+       } else {
+               arm_ldpx (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, 0);
+               /* sp += stack_offset */
+               g_assert (temp_regs & (1 << ARMREG_IP0));
+               if (temp_regs & (1 << ARMREG_IP1)) {
+                       code = emit_addx_sp_imm (code, stack_offset);
+               } else {
+                       int imm = stack_offset;
+
+                       /* Can't use addx_sp_imm () since we can't clobber ip0/ip1 */
+                       arm_addx_imm (code, ARMREG_IP0, ARMREG_SP, 0);
+                       while (imm > 256) {
+                               arm_addx_imm (code, ARMREG_IP0, ARMREG_IP0, 256);
+                               imm -= 256;
+                       }
+                       arm_addx_imm (code, ARMREG_SP, ARMREG_IP0, imm);
+               }
+       }
+       return code;
+}
+
+#define is_call_imm(diff) ((gint)(diff) >= -33554432 && (gint)(diff) <= 33554431)
+
+static guint8*
+emit_thunk (guint8 *code, gconstpointer target)
+{
+       guint8 *p = code;
+
+       arm_ldrx_lit (code, ARMREG_IP0, code + 8);
+       arm_brx (code, ARMREG_IP0);
+       *(guint64*)code = (guint64)target;
+
+       mono_arch_flush_icache (p, code - p);
+       return code;
+}
+
+static gpointer
+create_thunk (MonoCompile *cfg, MonoDomain *domain, guchar *code, const guchar *target)
+{
+       MonoJitInfo *ji;
+       MonoThunkJitInfo *info;
+       guint8 *thunks, *p;
+       int thunks_size;
+       guint8 *orig_target;
+       guint8 *target_thunk;
+
+       if (!domain)
+               domain = mono_domain_get ();
+
+       if (cfg) {
+               /*
+                * This can be called multiple times during JITting,
+                * save the current position in cfg->arch to avoid
+                * doing a O(n^2) search.
+                */
+               if (!cfg->arch.thunks) {
+                       cfg->arch.thunks = cfg->thunks;
+                       cfg->arch.thunks_size = cfg->thunk_area;
+               }
+               thunks = cfg->arch.thunks;
+               thunks_size = cfg->arch.thunks_size;
+               if (!thunks_size) {
+                       g_print ("thunk failed %p->%p, thunk space=%d method %s", code, target, thunks_size, mono_method_full_name (cfg->method, TRUE));
+                       g_assert_not_reached ();
+               }
+
+               g_assert (*(guint32*)thunks == 0);
+               emit_thunk (thunks, target);
+
+               cfg->arch.thunks += THUNK_SIZE;
+               cfg->arch.thunks_size -= THUNK_SIZE;
+
+               return thunks;
+       } else {
+               ji = mini_jit_info_table_find (domain, (char*)code, NULL);
+               g_assert (ji);
+               info = mono_jit_info_get_thunk_info (ji);
+               g_assert (info);
+
+               thunks = (guint8*)ji->code_start + info->thunks_offset;
+               thunks_size = info->thunks_size;
+
+               orig_target = mono_arch_get_call_target (code + 4);
+
+               mono_domain_lock (domain);
+
+               target_thunk = NULL;
+               if (orig_target >= thunks && orig_target < thunks + thunks_size) {
+                       /* The call already points to a thunk, because of trampolines etc. */
+                       target_thunk = orig_target;
+               } else {
+                       for (p = thunks; p < thunks + thunks_size; p += THUNK_SIZE) {
+                               if (((guint32*)p) [0] == 0) {
+                                       /* Free entry */
+                                       target_thunk = p;
+                                       break;
+                               } else if (((guint64*)p) [1] == (guint64)target) {
+                                       /* Thunk already points to target */
+                                       target_thunk = p;
+                                       break;
+                               }
+                       }
+               }
+
+               //printf ("THUNK: %p %p %p\n", code, target, target_thunk);
+
+               if (!target_thunk) {
+                       mono_domain_unlock (domain);
+                       g_print ("thunk failed %p->%p, thunk space=%d method %s", code, target, thunks_size, cfg ? mono_method_full_name (cfg->method, TRUE) : mono_method_full_name (jinfo_get_method (ji), TRUE));
+                       g_assert_not_reached ();
+               }
+
+               emit_thunk (target_thunk, target);
+
+               mono_domain_unlock (domain);
+
+               return target_thunk;
+       }
+}
+
+static void
+arm_patch_full (MonoCompile *cfg, MonoDomain *domain, guint8 *code, guint8 *target, int relocation)
+{
+       switch (relocation) {
+       case MONO_R_ARM64_B:
+               arm_b (code, target);
+               break;
+       case MONO_R_ARM64_BCC: {
+               int cond;
+
+               cond = arm_get_bcc_cond (code);
+               arm_bcc (code, cond, target);
+               break;
+       }
+       case MONO_R_ARM64_CBZ:
+               arm_set_cbz_target (code, target);
+               break;
+       case MONO_R_ARM64_IMM: {
+               guint64 imm = (guint64)target;
+               int dreg;
+
+               /* emit_imm64_template () */
+               dreg = arm_get_movzx_rd (code);
+               arm_movzx (code, dreg, imm & 0xffff, 0);
+               arm_movkx (code, dreg, (imm >> 16) & 0xffff, 16);
+               arm_movkx (code, dreg, (imm >> 32) & 0xffff, 32);
+               arm_movkx (code, dreg, (imm >> 48) & 0xffff, 48);
+               break;
+       }
+       case MONO_R_ARM64_BL:
+               if (arm_is_bl_disp (code, target)) {
+                       arm_bl (code, target);
+               } else {
+                       gpointer thunk;
+
+                       thunk = create_thunk (cfg, domain, code, target);
+                       g_assert (arm_is_bl_disp (code, thunk));
+                       arm_bl (code, thunk);                   
+               }
+               break;
+       default:
+               g_assert_not_reached ();
+       }
+}
+
+static void
+arm_patch_rel (guint8 *code, guint8 *target, int relocation)
+{
+       arm_patch_full (NULL, NULL, code, target, relocation);
+}
+
+void
+mono_arm_patch (guint8 *code, guint8 *target, int relocation)
+{
+       arm_patch_rel (code, target, relocation);
+}
+
+void
+mono_arch_patch_code_new (MonoCompile *cfg, MonoDomain *domain, guint8 *code, MonoJumpInfo *ji, gpointer target)
+{
+       guint8 *ip;
+
+       ip = ji->ip.i + code;
+
+       switch (ji->type) {
+       case MONO_PATCH_INFO_METHOD_JUMP:
+               /* ji->relocation is not set by the caller */
+               arm_patch_rel (ip, (guint8*)target, MONO_R_ARM64_B);
+               break;
+       default:
+               arm_patch_full (cfg, domain, ip, (guint8*)target, ji->relocation);
+               break;
+       }
+}
+
+void
+mono_arch_free_jit_tls_data (MonoJitTlsData *tls)
+{
+}
+
+void
+mono_arch_flush_register_windows (void)
+{
+}
+
+MonoMethod*
+mono_arch_find_imt_method (mgreg_t *regs, guint8 *code)
+{
+       return (gpointer)regs [MONO_ARCH_RGCTX_REG];
+}
+
+MonoVTable*
+mono_arch_find_static_call_vtable (mgreg_t *regs, guint8 *code)
+{
+       return (gpointer)regs [MONO_ARCH_RGCTX_REG];
+}
+
+mgreg_t
+mono_arch_context_get_int_reg (MonoContext *ctx, int reg)
+{
+       return ctx->regs [reg];
+}
+
+void
+mono_arch_context_set_int_reg (MonoContext *ctx, int reg, mgreg_t val)
+{
+       ctx->regs [reg] = val;
+}
+
+/*
+ * mono_arch_set_target:
+ *
+ *   Set the target architecture the JIT backend should generate code for, in the form
+ * of a GNU target triplet. Only used in AOT mode.
+ */
+void
+mono_arch_set_target (char *mtriple)
+{
+       if (strstr (mtriple, "darwin") || strstr (mtriple, "ios")) {
+               ios_abi = TRUE;
+       }
+}
+
+static void
+add_general (CallInfo *cinfo, ArgInfo *ainfo, int size, gboolean sign)
+{
+       if (cinfo->gr >= PARAM_REGS) {
+               ainfo->storage = ArgOnStack;
+               if (ios_abi) {
+                       /* Assume size == align */
+                       cinfo->stack_usage = ALIGN_TO (cinfo->stack_usage, size);
+                       ainfo->offset = cinfo->stack_usage;
+                       ainfo->slot_size = size;
+                       ainfo->sign = sign;
+                       cinfo->stack_usage += size;
+               } else {
+                       ainfo->offset = cinfo->stack_usage;
+                       ainfo->slot_size = 8;
+                       ainfo->sign = FALSE;
+                       /* Put arguments into 8 byte aligned stack slots */
+                       cinfo->stack_usage += 8;
+               }
+       } else {
+               ainfo->storage = ArgInIReg;
+               ainfo->reg = cinfo->gr;
+               cinfo->gr ++;
+       }
+}
+
+static void
+add_fp (CallInfo *cinfo, ArgInfo *ainfo, gboolean single)
+{
+       int size = single ? 4 : 8;
+
+       if (cinfo->fr >= FP_PARAM_REGS) {
+               ainfo->storage = single ? ArgOnStackR4 : ArgOnStackR8;
+               if (ios_abi) {
+                       cinfo->stack_usage = ALIGN_TO (cinfo->stack_usage, size);
+                       ainfo->offset = cinfo->stack_usage;
+                       ainfo->slot_size = size;
+                       cinfo->stack_usage += size;
+               } else {
+                       ainfo->offset = cinfo->stack_usage;
+                       ainfo->slot_size = 8;
+                       /* Put arguments into 8 byte aligned stack slots */
+                       cinfo->stack_usage += 8;
+               }
+       } else {
+               if (single)
+                       ainfo->storage = ArgInFRegR4;
+               else
+                       ainfo->storage = ArgInFReg;
+               ainfo->reg = cinfo->fr;
+               cinfo->fr ++;
+       }
+}
+
+static gboolean
+is_hfa (MonoType *t, int *out_nfields, int *out_esize, int *field_offsets)
+{
+       MonoClass *klass;
+       gpointer iter;
+       MonoClassField *field;
+       MonoType *ftype, *prev_ftype = NULL;
+       int i, nfields = 0;
+
+       klass = mono_class_from_mono_type (t);
+       iter = NULL;
+       while ((field = mono_class_get_fields (klass, &iter))) {
+               if (field->type->attrs & FIELD_ATTRIBUTE_STATIC)
+                       continue;
+               ftype = mono_field_get_type (field);
+               ftype = mini_get_underlying_type (ftype);
+
+               if (MONO_TYPE_ISSTRUCT (ftype)) {
+                       int nested_nfields, nested_esize;
+                       int nested_field_offsets [16];
+
+                       if (!is_hfa (ftype, &nested_nfields, &nested_esize, nested_field_offsets))
+                               return FALSE;
+                       if (nested_esize == 4)
+                               ftype = &mono_defaults.single_class->byval_arg;
+                       else
+                               ftype = &mono_defaults.double_class->byval_arg;
+                       if (prev_ftype && prev_ftype->type != ftype->type)
+                               return FALSE;
+                       prev_ftype = ftype;
+                       for (i = 0; i < nested_nfields; ++i) {
+                               if (nfields + i < 4)
+                                       field_offsets [nfields + i] = field->offset - sizeof (MonoObject) + nested_field_offsets [i];
+                       }
+                       nfields += nested_nfields;
+               } else {
+                       if (!(!ftype->byref && (ftype->type == MONO_TYPE_R4 || ftype->type == MONO_TYPE_R8)))
+                               return FALSE;
+                       if (prev_ftype && prev_ftype->type != ftype->type)
+                               return FALSE;
+                       prev_ftype = ftype;
+                       if (nfields < 4)
+                               field_offsets [nfields] = field->offset - sizeof (MonoObject);
+                       nfields ++;
+               }
+       }
+       if (nfields == 0 || nfields > 4)
+               return FALSE;
+       *out_nfields = nfields;
+       *out_esize = prev_ftype->type == MONO_TYPE_R4 ? 4 : 8;
+       return TRUE;
+}
+
+static void
+add_valuetype (CallInfo *cinfo, ArgInfo *ainfo, MonoType *t)
+{
+       int i, size, align_size, nregs, nfields, esize;
+       int field_offsets [16];
+       guint32 align;
+
+       size = mini_type_stack_size_full (t, &align, cinfo->pinvoke);
+       align_size = ALIGN_TO (size, 8);
+
+       nregs = align_size / 8;
+       if (is_hfa (t, &nfields, &esize, field_offsets)) {
+               /*
+                * The struct might include nested float structs aligned at 8,
+                * so need to keep track of the offsets of the individual fields.
+                */
+               if (cinfo->fr + nfields <= FP_PARAM_REGS) {
+                       ainfo->storage = ArgHFA;
+                       ainfo->reg = cinfo->fr;
+                       ainfo->nregs = nfields;
+                       ainfo->size = size;
+                       ainfo->esize = esize;
+                       for (i = 0; i < nfields; ++i)
+                               ainfo->foffsets [i] = field_offsets [i];
+                       cinfo->fr += ainfo->nregs;
+               } else {
+                       ainfo->nfregs_to_skip = FP_PARAM_REGS > cinfo->fr ? FP_PARAM_REGS - cinfo->fr : 0;
+                       cinfo->fr = FP_PARAM_REGS;
+                       size = ALIGN_TO (size, 8);
+                       ainfo->storage = ArgVtypeOnStack;
+                       ainfo->offset = cinfo->stack_usage;
+                       ainfo->size = size;
+                       ainfo->hfa = TRUE;
+                       ainfo->nregs = nfields;
+                       ainfo->esize = esize;
+                       cinfo->stack_usage += size;
+               }
+               return;
+       }
+
+       if (align_size > 16) {
+               ainfo->storage = ArgVtypeByRef;
+               ainfo->size = size;
+               return;
+       }
+
+       if (cinfo->gr + nregs > PARAM_REGS) {
+               size = ALIGN_TO (size, 8);
+               ainfo->storage = ArgVtypeOnStack;
+               ainfo->offset = cinfo->stack_usage;
+               ainfo->size = size;
+               cinfo->stack_usage += size;
+               cinfo->gr = PARAM_REGS;
+       } else {
+               ainfo->storage = ArgVtypeInIRegs;
+               ainfo->reg = cinfo->gr;
+               ainfo->nregs = nregs;
+               ainfo->size = size;
+               cinfo->gr += nregs;
+       }
+}
+
+static void
+add_param (CallInfo *cinfo, ArgInfo *ainfo, MonoType *t)
+{
+       MonoType *ptype;
+
+       ptype = mini_get_underlying_type (t);
+       switch (ptype->type) {
+       case MONO_TYPE_I1:
+               add_general (cinfo, ainfo, 1, TRUE);
+               break;
+       case MONO_TYPE_BOOLEAN:
+       case MONO_TYPE_U1:
+               add_general (cinfo, ainfo, 1, FALSE);
+               break;
+       case MONO_TYPE_I2:
+               add_general (cinfo, ainfo, 2, TRUE);
+               break;
+       case MONO_TYPE_U2:
+       case MONO_TYPE_CHAR:
+               add_general (cinfo, ainfo, 2, FALSE);
+               break;
+       case MONO_TYPE_I4:
+               add_general (cinfo, ainfo, 4, TRUE);
+               break;
+       case MONO_TYPE_U4:
+               add_general (cinfo, ainfo, 4, FALSE);
+               break;
+       case MONO_TYPE_I:
+       case MONO_TYPE_U:
+       case MONO_TYPE_PTR:
+       case MONO_TYPE_FNPTR:
+       case MONO_TYPE_CLASS:
+       case MONO_TYPE_OBJECT:
+       case MONO_TYPE_SZARRAY:
+       case MONO_TYPE_ARRAY:
+       case MONO_TYPE_STRING:
+       case MONO_TYPE_U8:
+       case MONO_TYPE_I8:
+               add_general (cinfo, ainfo, 8, FALSE);
+               break;
+       case MONO_TYPE_R8:
+               add_fp (cinfo, ainfo, FALSE);
+               break;
+       case MONO_TYPE_R4:
+               add_fp (cinfo, ainfo, TRUE);
+               break;
+       case MONO_TYPE_VALUETYPE:
+       case MONO_TYPE_TYPEDBYREF:
+               add_valuetype (cinfo, ainfo, ptype);
+               break;
+       case MONO_TYPE_VOID:
+               ainfo->storage = ArgNone;
+               break;
+       case MONO_TYPE_GENERICINST:
+               if (!mono_type_generic_inst_is_valuetype (ptype)) {
+                       add_general (cinfo, ainfo, 8, FALSE);
+               } else if (mini_is_gsharedvt_variable_type (ptype)) {
+                       /*
+                        * Treat gsharedvt arguments as large vtypes
+                        */
+                       ainfo->storage = ArgVtypeByRef;
+                       ainfo->gsharedvt = TRUE;
+               } else {
+                       add_valuetype (cinfo, ainfo, ptype);
+               }
+               break;
+       case MONO_TYPE_VAR:
+       case MONO_TYPE_MVAR:
+               g_assert (mini_is_gsharedvt_type (ptype));
+               ainfo->storage = ArgVtypeByRef;
+               ainfo->gsharedvt = TRUE;
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+}
+
+/*
+ * get_call_info:
+ *
+ *  Obtain information about a call according to the calling convention.
+ */
+static CallInfo*
+get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
+{
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
+       int n, pstart, pindex;
+
+       n = sig->hasthis + sig->param_count;
+
+       if (mp)
+               cinfo = mono_mempool_alloc0 (mp, sizeof (CallInfo) + (sizeof (ArgInfo) * n));
+       else
+               cinfo = g_malloc0 (sizeof (CallInfo) + (sizeof (ArgInfo) * n));
+
+       cinfo->nargs = n;
+       cinfo->pinvoke = sig->pinvoke;
+
+       /* Return value */
+       add_param (cinfo, &cinfo->ret, sig->ret);
+       if (cinfo->ret.storage == ArgVtypeByRef)
+               cinfo->ret.reg = ARMREG_R8;
+       /* Reset state */
+       cinfo->gr = 0;
+       cinfo->fr = 0;
+       cinfo->stack_usage = 0;
+
+       /* Parameters */
+       if (sig->hasthis)
+               add_general (cinfo, cinfo->args + 0, 8, FALSE);
+       pstart = 0;
+       for (pindex = pstart; pindex < sig->param_count; ++pindex) {
+               ainfo = cinfo->args + sig->hasthis + pindex;
+
+               if ((sig->call_convention == MONO_CALL_VARARG) && (pindex == sig->sentinelpos)) {
+                       /* Prevent implicit arguments and sig_cookie from
+                          being passed in registers */
+                       cinfo->gr = PARAM_REGS;
+                       cinfo->fr = FP_PARAM_REGS;
+                       /* Emit the signature cookie just before the implicit arguments */
+                       add_param (cinfo, &cinfo->sig_cookie, &mono_defaults.int_class->byval_arg);
+               }
+
+               add_param (cinfo, ainfo, sig->params [pindex]);
+               if (ainfo->storage == ArgVtypeByRef) {
+                       /* Pass the argument address in the next register */
+                       if (cinfo->gr >= PARAM_REGS) {
+                               ainfo->storage = ArgVtypeByRefOnStack;
+                               ainfo->offset = cinfo->stack_usage;
+                               cinfo->stack_usage += 8;
+                       } else {
+                               ainfo->reg = cinfo->gr;
+                               cinfo->gr ++;
+                       }
+               }
+       }
+
+       /* Handle the case where there are no implicit arguments */
+       if ((sig->call_convention == MONO_CALL_VARARG) && (pindex == sig->sentinelpos)) {
+               /* Prevent implicit arguments and sig_cookie from
+                  being passed in registers */
+               cinfo->gr = PARAM_REGS;
+               cinfo->fr = FP_PARAM_REGS;
+               /* Emit the signature cookie just before the implicit arguments */
+               add_param (cinfo, &cinfo->sig_cookie, &mono_defaults.int_class->byval_arg);
+       }
+
+       cinfo->stack_usage = ALIGN_TO (cinfo->stack_usage, MONO_ARCH_FRAME_ALIGNMENT);
+
+       return cinfo;
+}
+
+typedef struct {
+       MonoMethodSignature *sig;
+       CallInfo *cinfo;
+       MonoType *rtype;
+       MonoType **param_types;
+       int n_fpargs, n_fpret;
+} ArchDynCallInfo;
+
+static gboolean
+dyn_call_supported (CallInfo *cinfo, MonoMethodSignature *sig)
+{
+       int i;
+
+       if (sig->hasthis + sig->param_count > PARAM_REGS + DYN_CALL_STACK_ARGS)
+               return FALSE;
+
+       // FIXME: Add more cases
+       switch (cinfo->ret.storage) {
+       case ArgNone:
+       case ArgInIReg:
+       case ArgInFReg:
+       case ArgInFRegR4:
+       case ArgVtypeByRef:
+               break;
+       case ArgVtypeInIRegs:
+               if (cinfo->ret.nregs > 2)
+                       return FALSE;
+               break;
+       case ArgHFA:
+               break;
+       default:
+               return FALSE;
+       }
+
+       for (i = 0; i < cinfo->nargs; ++i) {
+               ArgInfo *ainfo = &cinfo->args [i];
+
+               switch (ainfo->storage) {
+               case ArgInIReg:
+               case ArgVtypeInIRegs:
+               case ArgInFReg:
+               case ArgInFRegR4:
+               case ArgHFA:
+               case ArgVtypeByRef:
+                       break;
+               case ArgOnStack:
+                       if (ainfo->offset >= DYN_CALL_STACK_ARGS * sizeof (mgreg_t))
+                               return FALSE;
+                       break;
+               default:
+                       return FALSE;
+               }
+       }
+
+       return TRUE;
+}
+
+MonoDynCallInfo*
+mono_arch_dyn_call_prepare (MonoMethodSignature *sig)
+{
+       ArchDynCallInfo *info;
+       CallInfo *cinfo;
+       int i;
+
+       cinfo = get_call_info (NULL, sig);
+
+       if (!dyn_call_supported (cinfo, sig)) {
+               g_free (cinfo);
+               return NULL;
+       }
+
+       info = g_new0 (ArchDynCallInfo, 1);
+       // FIXME: Preprocess the info to speed up start_dyn_call ()
+       info->sig = sig;
+       info->cinfo = cinfo;
+       info->rtype = mini_get_underlying_type (sig->ret);
+       info->param_types = g_new0 (MonoType*, sig->param_count);
+       for (i = 0; i < sig->param_count; ++i)
+               info->param_types [i] = mini_get_underlying_type (sig->params [i]);
+
+       switch (cinfo->ret.storage) {
+       case ArgInFReg:
+       case ArgInFRegR4:
+               info->n_fpret = 1;
+               break;
+       case ArgHFA:
+               info->n_fpret = cinfo->ret.nregs;
+               break;
+       default:
+               break;
+       }
+       
+       return (MonoDynCallInfo*)info;
+}
+
+void
+mono_arch_dyn_call_free (MonoDynCallInfo *info)
+{
+       ArchDynCallInfo *ainfo = (ArchDynCallInfo*)info;
+
+       g_free (ainfo->cinfo);
+       g_free (ainfo->param_types);
+       g_free (ainfo);
+}
+
+static double
+bitcast_r4_to_r8 (float f)
+{
+       float *p = &f;
+
+       return *(double*)p;
+}
+
+static float
+bitcast_r8_to_r4 (double f)
+{
+       double *p = &f;
+
+       return *(float*)p;
+}
+
+void
+mono_arch_start_dyn_call (MonoDynCallInfo *info, gpointer **args, guint8 *ret, guint8 *buf, int buf_len)
+{
+       ArchDynCallInfo *dinfo = (ArchDynCallInfo*)info;
+       DynCallArgs *p = (DynCallArgs*)buf;
+       int aindex, arg_index, greg, i, pindex;
+       MonoMethodSignature *sig = dinfo->sig;
+       CallInfo *cinfo = dinfo->cinfo;
+       int buffer_offset = 0;
+
+       g_assert (buf_len >= sizeof (DynCallArgs));
+
+       p->res = 0;
+       p->ret = ret;
+       p->n_fpargs = dinfo->n_fpargs;
+       p->n_fpret = dinfo->n_fpret;
+
+       arg_index = 0;
+       greg = 0;
+       pindex = 0;
+
+       if (sig->hasthis)
+               p->regs [greg ++] = (mgreg_t)*(args [arg_index ++]);
+
+       if (cinfo->ret.storage == ArgVtypeByRef)
+               p->regs [ARMREG_R8] = (mgreg_t)ret;
+
+       for (aindex = pindex; aindex < sig->param_count; aindex++) {
+               MonoType *t = dinfo->param_types [aindex];
+               gpointer *arg = args [arg_index ++];
+               ArgInfo *ainfo = &cinfo->args [aindex + sig->hasthis];
+               int slot = -1;
+
+               if (ainfo->storage == ArgOnStack) {
+                       slot = PARAM_REGS + 1 + (ainfo->offset / sizeof (mgreg_t));
+               } else {
+                       slot = ainfo->reg;
+               }
+
+               if (t->byref) {
+                       p->regs [slot] = (mgreg_t)*arg;
+                       continue;
+               }
+
+               if (ios_abi && ainfo->storage == ArgOnStack) {
+                       guint8 *stack_arg = (guint8*)&(p->regs [PARAM_REGS + 1]) + ainfo->offset;
+                       gboolean handled = TRUE;
+
+                       /* Special case arguments smaller than 1 machine word */
+                       switch (t->type) {
+                       case MONO_TYPE_BOOLEAN:
+                       case MONO_TYPE_U1:
+                               *(guint8*)stack_arg = *(guint8*)arg;
+                               break;
+                       case MONO_TYPE_I1:
+                               *(gint8*)stack_arg = *(gint8*)arg;
+                               break;
+                       case MONO_TYPE_U2:
+                       case MONO_TYPE_CHAR:
+                               *(guint16*)stack_arg = *(guint16*)arg;
+                               break;
+                       case MONO_TYPE_I2:
+                               *(gint16*)stack_arg = *(gint16*)arg;
+                               break;
+                       case MONO_TYPE_I4:
+                               *(gint32*)stack_arg = *(gint32*)arg;
+                               break;
+                       case MONO_TYPE_U4:
+                               *(guint32*)stack_arg = *(guint32*)arg;
+                               break;
+                       default:
+                               handled = FALSE;
+                               break;
+                       }
+                       if (handled)
+                               continue;
+               }
+
+               switch (t->type) {
+               case MONO_TYPE_STRING:
+               case MONO_TYPE_CLASS:
+               case MONO_TYPE_ARRAY:
+               case MONO_TYPE_SZARRAY:
+               case MONO_TYPE_OBJECT:
+               case MONO_TYPE_PTR:
+               case MONO_TYPE_I:
+               case MONO_TYPE_U:
+               case MONO_TYPE_I8:
+               case MONO_TYPE_U8:
+                       p->regs [slot] = (mgreg_t)*arg;
+                       break;
+               case MONO_TYPE_BOOLEAN:
+               case MONO_TYPE_U1:
+                       p->regs [slot] = *(guint8*)arg;
+                       break;
+               case MONO_TYPE_I1:
+                       p->regs [slot] = *(gint8*)arg;
+                       break;
+               case MONO_TYPE_I2:
+                       p->regs [slot] = *(gint16*)arg;
+                       break;
+               case MONO_TYPE_U2:
+               case MONO_TYPE_CHAR:
+                       p->regs [slot] = *(guint16*)arg;
+                       break;
+               case MONO_TYPE_I4:
+                       p->regs [slot] = *(gint32*)arg;
+                       break;
+               case MONO_TYPE_U4:
+                       p->regs [slot] = *(guint32*)arg;
+                       break;
+               case MONO_TYPE_R4:
+                       p->fpregs [ainfo->reg] = bitcast_r4_to_r8 (*(float*)arg);
+                       p->n_fpargs ++;
+                       break;
+               case MONO_TYPE_R8:
+                       p->fpregs [ainfo->reg] = *(double*)arg;
+                       p->n_fpargs ++;
+                       break;
+               case MONO_TYPE_GENERICINST:
+                       if (MONO_TYPE_IS_REFERENCE (t)) {
+                               p->regs [slot] = (mgreg_t)*arg;
+                               break;
+                       } else {
+                               if (t->type == MONO_TYPE_GENERICINST && mono_class_is_nullable (mono_class_from_mono_type (t))) {
+                                       MonoClass *klass = mono_class_from_mono_type (t);
+                                       guint8 *nullable_buf;
+                                       int size;
+
+                                       /*
+                                        * Use p->buffer as a temporary buffer since the data needs to be available after this call
+                                        * if the nullable param is passed by ref.
+                                        */
+                                       size = mono_class_value_size (klass, NULL);
+                                       nullable_buf = p->buffer + buffer_offset;
+                                       buffer_offset += size;
+                                       g_assert (buffer_offset <= 256);
+
+                                       /* The argument pointed to by arg is either a boxed vtype or null */
+                                       mono_nullable_init (nullable_buf, (MonoObject*)arg, klass);
+
+                                       arg = (gpointer*)nullable_buf;
+                                       /* Fall though */
+                               } else {
+                                       /* Fall though */
+                               }
+                       }
+               case MONO_TYPE_VALUETYPE:
+                       switch (ainfo->storage) {
+                       case ArgVtypeInIRegs:
+                               for (i = 0; i < ainfo->nregs; ++i)
+                                       p->regs [slot ++] = ((mgreg_t*)arg) [i];
+                               break;
+                       case ArgHFA:
+                               if (ainfo->esize == 4) {
+                                       for (i = 0; i < ainfo->nregs; ++i)
+                                               p->fpregs [ainfo->reg + i] = bitcast_r4_to_r8 (((float*)arg) [ainfo->foffsets [i] / 4]);
+                               } else {
+                                       for (i = 0; i < ainfo->nregs; ++i)
+                                               p->fpregs [ainfo->reg + i] = ((double*)arg) [ainfo->foffsets [i] / 8];
+                               }
+                               p->n_fpargs += ainfo->nregs;
+                               break;
+                       case ArgVtypeByRef:
+                               p->regs [slot] = (mgreg_t)arg;
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                               break;
+                       }
+                       break;
+               default:
+                       g_assert_not_reached ();
+               }
+       }
+}
+
+void
+mono_arch_finish_dyn_call (MonoDynCallInfo *info, guint8 *buf)
+{
+       ArchDynCallInfo *ainfo = (ArchDynCallInfo*)info;
+       CallInfo *cinfo = ainfo->cinfo;
+       DynCallArgs *args = (DynCallArgs*)buf;
+       MonoType *ptype = ainfo->rtype;
+       guint8 *ret = args->ret;
+       mgreg_t res = args->res;
+       mgreg_t res2 = args->res2;
+       int i;
+
+       if (cinfo->ret.storage == ArgVtypeByRef)
+               return;
+
+       switch (ptype->type) {
+       case MONO_TYPE_VOID:
+               *(gpointer*)ret = NULL;
+               break;
+       case MONO_TYPE_STRING:
+       case MONO_TYPE_CLASS:
+       case MONO_TYPE_ARRAY:
+       case MONO_TYPE_SZARRAY:
+       case MONO_TYPE_OBJECT:
+       case MONO_TYPE_I:
+       case MONO_TYPE_U:
+       case MONO_TYPE_PTR:
+               *(gpointer*)ret = (gpointer)res;
+               break;
+       case MONO_TYPE_I1:
+               *(gint8*)ret = res;
+               break;
+       case MONO_TYPE_U1:
+       case MONO_TYPE_BOOLEAN:
+               *(guint8*)ret = res;
+               break;
+       case MONO_TYPE_I2:
+               *(gint16*)ret = res;
+               break;
+       case MONO_TYPE_U2:
+       case MONO_TYPE_CHAR:
+               *(guint16*)ret = res;
+               break;
+       case MONO_TYPE_I4:
+               *(gint32*)ret = res;
+               break;
+       case MONO_TYPE_U4:
+               *(guint32*)ret = res;
+               break;
+       case MONO_TYPE_I8:
+       case MONO_TYPE_U8:
+               *(guint64*)ret = res;
+               break;
+       case MONO_TYPE_R4:
+               *(float*)ret = bitcast_r8_to_r4 (args->fpregs [0]);
+               break;
+       case MONO_TYPE_R8:
+               *(double*)ret = args->fpregs [0];
+               break;
+       case MONO_TYPE_GENERICINST:
+               if (MONO_TYPE_IS_REFERENCE (ptype)) {
+                       *(gpointer*)ret = (gpointer)res;
+                       break;
+               } else {
+                       /* Fall though */
+               }
+       case MONO_TYPE_VALUETYPE:
+               switch (ainfo->cinfo->ret.storage) {
+               case ArgVtypeInIRegs:
+                       *(mgreg_t*)ret = res;
+                       if (ainfo->cinfo->ret.nregs > 1)
+                               ((mgreg_t*)ret) [1] = res2;
+                       break;
+               case ArgHFA:
+                       /* Use the same area for returning fp values */
+                       if (cinfo->ret.esize == 4) {
+                               for (i = 0; i < cinfo->ret.nregs; ++i)
+                                       ((float*)ret) [cinfo->ret.foffsets [i] / 4] = bitcast_r8_to_r4 (args->fpregs [i]);
+                       } else {
+                               for (i = 0; i < cinfo->ret.nregs; ++i)
+                                       ((double*)ret) [cinfo->ret.foffsets [i] / 8] = args->fpregs [i];
+                       }
+                       break;
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+               break;
+       default:
+               g_assert_not_reached ();
+       }
+}
+
+#if __APPLE__
+void sys_icache_invalidate (void *start, size_t len);
+#endif
+
+void
+mono_arch_flush_icache (guint8 *code, gint size)
+{
+#ifndef MONO_CROSS_COMPILE
+#if __APPLE__
+       sys_icache_invalidate (code, size);
+#else
+       __clear_cache (code, code + size);
+#endif
+#endif
+}
+
+#ifndef DISABLE_JIT
+
+gboolean
+mono_arch_opcode_needs_emulation (MonoCompile *cfg, int opcode)
+{
+       NOT_IMPLEMENTED;
+       return FALSE;
+}
+
+GList *
+mono_arch_get_allocatable_int_vars (MonoCompile *cfg)
+{
+       GList *vars = NULL;
+       int i;
+
+       for (i = 0; i < cfg->num_varinfo; i++) {
+               MonoInst *ins = cfg->varinfo [i];
+               MonoMethodVar *vmv = MONO_VARINFO (cfg, i);
+
+               /* unused vars */
+               if (vmv->range.first_use.abs_pos >= vmv->range.last_use.abs_pos)
+                       continue;
+
+               if ((ins->flags & (MONO_INST_IS_DEAD|MONO_INST_VOLATILE|MONO_INST_INDIRECT)) || 
+                   (ins->opcode != OP_LOCAL && ins->opcode != OP_ARG))
+                       continue;
+
+               if (mono_is_regsize_var (ins->inst_vtype)) {
+                       g_assert (MONO_VARINFO (cfg, i)->reg == -1);
+                       g_assert (i == vmv->idx);
+                       vars = g_list_prepend (vars, vmv);
+               }
+       }
+
+       vars = mono_varlist_sort (cfg, vars, 0);
+
+       return vars;
+}
+
+GList *
+mono_arch_get_global_int_regs (MonoCompile *cfg)
+{
+       GList *regs = NULL;
+       int i;
+
+       /* r28 is reserved for cfg->arch.args_reg */
+       /* r27 is reserved for the imt argument */
+       for (i = ARMREG_R19; i <= ARMREG_R26; ++i)
+               regs = g_list_prepend (regs, GUINT_TO_POINTER (i));
+
+       return regs;
+}
+
+guint32
+mono_arch_regalloc_cost (MonoCompile *cfg, MonoMethodVar *vmv)
+{
+       MonoInst *ins = cfg->varinfo [vmv->idx];
+
+       if (ins->opcode == OP_ARG)
+               return 1;
+       else
+               return 2;
+}
+
+void
+mono_arch_create_vars (MonoCompile *cfg)
+{
+       MonoMethodSignature *sig;
+       CallInfo *cinfo;
+
+       sig = mono_method_signature (cfg->method);
+       if (!cfg->arch.cinfo)
+               cfg->arch.cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = cfg->arch.cinfo;
+
+       if (cinfo->ret.storage == ArgVtypeByRef) {
+               cfg->vret_addr = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_LOCAL);
+               cfg->vret_addr->flags |= MONO_INST_VOLATILE;
+       }
+
+       if (cfg->gen_sdb_seq_points) {
+               MonoInst *ins;
+
+               if (cfg->compile_aot) {
+                       ins = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_LOCAL);
+                       ins->flags |= MONO_INST_VOLATILE;
+                       cfg->arch.seq_point_info_var = ins;
+               }
+
+               ins = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_LOCAL);
+               ins->flags |= MONO_INST_VOLATILE;
+               cfg->arch.ss_tramp_var = ins;
+
+               ins = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_LOCAL);
+               ins->flags |= MONO_INST_VOLATILE;
+               cfg->arch.bp_tramp_var = ins;
+       }
+
+       if (cfg->method->save_lmf) {
+               cfg->create_lmf_var = TRUE;
+               cfg->lmf_ir = TRUE;
+#ifndef TARGET_MACH
+               cfg->lmf_ir_mono_lmf = TRUE;
+#endif
+       }
+}
+
+void
+mono_arch_allocate_vars (MonoCompile *cfg)
+{
+       MonoMethodSignature *sig;
+       MonoInst *ins;
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
+       int i, offset, size, align;
+       guint32 locals_stack_size, locals_stack_align;
+       gint32 *offsets;
+
+       /*
+        * Allocate arguments and locals to either register (OP_REGVAR) or to a stack slot (OP_REGOFFSET).
+        * Compute cfg->stack_offset and update cfg->used_int_regs.
+        */
+
+       sig = mono_method_signature (cfg->method);
+
+       if (!cfg->arch.cinfo)
+               cfg->arch.cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = cfg->arch.cinfo;
+
+       /*
+        * The ARM64 ABI always uses a frame pointer.
+        * The instruction set prefers positive offsets, so fp points to the bottom of the
+        * frame, and stack slots are at positive offsets.
+        * If some arguments are received on the stack, their offsets relative to fp can
+        * not be computed right now because the stack frame might grow due to spilling
+        * done by the local register allocator. To solve this, we reserve a register
+        * which points to them.
+        * The stack frame looks like this:
+        * args_reg -> <bottom of parent frame>
+        *             <locals etc>
+        *       fp -> <saved fp+lr>
+     *       sp -> <localloc/params area>
+        */
+       cfg->frame_reg = ARMREG_FP;
+       cfg->flags |= MONO_CFG_HAS_SPILLUP;
+       offset = 0;
+
+       /* Saved fp+lr */
+       offset += 16;
+
+       if (cinfo->stack_usage) {
+               g_assert (!(cfg->used_int_regs & (1 << ARMREG_R28)));
+               cfg->arch.args_reg = ARMREG_R28;
+               cfg->used_int_regs |= 1 << ARMREG_R28;
+       }
+
+       if (cfg->method->save_lmf) {
+               /* The LMF var is allocated normally */
+       } else {
+               /* Callee saved regs */
+               cfg->arch.saved_gregs_offset = offset;
+               for (i = 0; i < 32; ++i)
+                       if ((MONO_ARCH_CALLEE_SAVED_REGS & (1 << i)) && (cfg->used_int_regs & (1 << i)))
+                               offset += 8;
+       }
+
+       /* Return value */
+       switch (cinfo->ret.storage) {
+       case ArgNone:
+               break;
+       case ArgInIReg:
+       case ArgInFReg:
+       case ArgInFRegR4:
+               cfg->ret->opcode = OP_REGVAR;
+               cfg->ret->dreg = cinfo->ret.reg;
+               break;
+       case ArgVtypeInIRegs:
+       case ArgHFA:
+               /* Allocate a local to hold the result, the epilog will copy it to the correct place */
+               cfg->ret->opcode = OP_REGOFFSET;
+               cfg->ret->inst_basereg = cfg->frame_reg;
+               cfg->ret->inst_offset = offset;
+               if (cinfo->ret.storage == ArgHFA)
+                       // FIXME:
+                       offset += 64;
+               else
+                       offset += 16;
+               break;
+       case ArgVtypeByRef:
+               /* This variable will be initalized in the prolog from R8 */
+               cfg->vret_addr->opcode = OP_REGOFFSET;
+               cfg->vret_addr->inst_basereg = cfg->frame_reg;
+               cfg->vret_addr->inst_offset = offset;
+               offset += 8;
+               if (G_UNLIKELY (cfg->verbose_level > 1)) {
+                       printf ("vret_addr =");
+                       mono_print_ins (cfg->vret_addr);
+               }
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+
+       /* Arguments */
+       for (i = 0; i < sig->param_count + sig->hasthis; ++i) {
+               ainfo = cinfo->args + i;
+
+               ins = cfg->args [i];
+               if (ins->opcode == OP_REGVAR)
+                       continue;
+
+               ins->opcode = OP_REGOFFSET;
+               ins->inst_basereg = cfg->frame_reg;
+
+               switch (ainfo->storage) {
+               case ArgInIReg:
+               case ArgInFReg:
+               case ArgInFRegR4:
+                       // FIXME: Use nregs/size
+                       /* These will be copied to the stack in the prolog */
+                       ins->inst_offset = offset;
+                       offset += 8;
+                       break;
+               case ArgOnStack:
+               case ArgOnStackR4:
+               case ArgOnStackR8:
+               case ArgVtypeOnStack:
+                       /* These are in the parent frame */
+                       g_assert (cfg->arch.args_reg);
+                       ins->inst_basereg = cfg->arch.args_reg;
+                       ins->inst_offset = ainfo->offset;
+                       break;
+               case ArgVtypeInIRegs:
+               case ArgHFA:
+                       ins->opcode = OP_REGOFFSET;
+                       ins->inst_basereg = cfg->frame_reg;
+                       /* These arguments are saved to the stack in the prolog */
+                       ins->inst_offset = offset;
+                       if (cfg->verbose_level >= 2)
+                               printf ("arg %d allocated to %s+0x%0x.\n", i, mono_arch_regname (ins->inst_basereg), (int)ins->inst_offset);
+                       if (ainfo->storage == ArgHFA)
+                               // FIXME:
+                               offset += 64;
+                       else
+                               offset += 16;
+                       break;
+               case ArgVtypeByRefOnStack: {
+                       MonoInst *vtaddr;
+
+                       if (ainfo->gsharedvt) {
+                               ins->opcode = OP_REGOFFSET;
+                               ins->inst_basereg = cfg->arch.args_reg;
+                               ins->inst_offset = ainfo->offset;
+                               break;
+                       }
+
+                       /* The vtype address is in the parent frame */
+                       g_assert (cfg->arch.args_reg);
+                       MONO_INST_NEW (cfg, vtaddr, 0);
+                       vtaddr->opcode = OP_REGOFFSET;
+                       vtaddr->inst_basereg = cfg->arch.args_reg;
+                       vtaddr->inst_offset = ainfo->offset;
+
+                       /* Need an indirection */
+                       ins->opcode = OP_VTARG_ADDR;
+                       ins->inst_left = vtaddr;
+                       break;
+               }
+               case ArgVtypeByRef: {
+                       MonoInst *vtaddr;
+
+                       if (ainfo->gsharedvt) {
+                               ins->opcode = OP_REGOFFSET;
+                               ins->inst_basereg = cfg->frame_reg;
+                               ins->inst_offset = offset;
+                               offset += 8;
+                               break;
+                       }
+
+                       /* The vtype address is in a register, will be copied to the stack in the prolog */
+                       MONO_INST_NEW (cfg, vtaddr, 0);
+                       vtaddr->opcode = OP_REGOFFSET;
+                       vtaddr->inst_basereg = cfg->frame_reg;
+                       vtaddr->inst_offset = offset;
+                       offset += 8;
+
+                       /* Need an indirection */
+                       ins->opcode = OP_VTARG_ADDR;
+                       ins->inst_left = vtaddr;
+                       break;
+               }
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+       }
+
+       /* Allocate these first so they have a small offset, OP_SEQ_POINT depends on this */
+       // FIXME: Allocate these to registers
+       ins = cfg->arch.seq_point_info_var;
+       if (ins) {
+               size = 8;
+               align = 8;
+               offset += align - 1;
+               offset &= ~(align - 1);
+               ins->opcode = OP_REGOFFSET;
+               ins->inst_basereg = cfg->frame_reg;
+               ins->inst_offset = offset;
+               offset += size;
+       }
+       ins = cfg->arch.ss_tramp_var;
+       if (ins) {
+               size = 8;
+               align = 8;
+               offset += align - 1;
+               offset &= ~(align - 1);
+               ins->opcode = OP_REGOFFSET;
+               ins->inst_basereg = cfg->frame_reg;
+               ins->inst_offset = offset;
+               offset += size;
+       }
+       ins = cfg->arch.bp_tramp_var;
+       if (ins) {
+               size = 8;
+               align = 8;
+               offset += align - 1;
+               offset &= ~(align - 1);
+               ins->opcode = OP_REGOFFSET;
+               ins->inst_basereg = cfg->frame_reg;
+               ins->inst_offset = offset;
+               offset += size;
+       }
+
+       /* Locals */
+       offsets = mono_allocate_stack_slots (cfg, FALSE, &locals_stack_size, &locals_stack_align);
+       if (locals_stack_align)
+               offset = ALIGN_TO (offset, locals_stack_align);
+
+       for (i = cfg->locals_start; i < cfg->num_varinfo; i++) {
+               if (offsets [i] != -1) {
+                       ins = cfg->varinfo [i];
+                       ins->opcode = OP_REGOFFSET;
+                       ins->inst_basereg = cfg->frame_reg;
+                       ins->inst_offset = offset + offsets [i];
+                       //printf ("allocated local %d to ", i); mono_print_tree_nl (ins);
+               }
+       }
+       offset += locals_stack_size;
+
+       offset = ALIGN_TO (offset, MONO_ARCH_FRAME_ALIGNMENT);
+
+       cfg->stack_offset = offset;
+}
+
+#ifdef ENABLE_LLVM
+LLVMCallInfo*
+mono_arch_get_llvm_call_info (MonoCompile *cfg, MonoMethodSignature *sig)
+{
+       int i, n;
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
+       LLVMCallInfo *linfo;
+
+       n = sig->param_count + sig->hasthis;
+
+       cinfo = get_call_info (cfg->mempool, sig);
+
+       linfo = mono_mempool_alloc0 (cfg->mempool, sizeof (LLVMCallInfo) + (sizeof (LLVMArgInfo) * n));
+
+       switch (cinfo->ret.storage) {
+       case ArgInIReg:
+       case ArgInFReg:
+       case ArgInFRegR4:
+       case ArgNone:
+               break;
+       case ArgVtypeByRef:
+               linfo->ret.storage = LLVMArgVtypeByRef;
+               break;
+               //
+               // FIXME: This doesn't work yet since the llvm backend represents these types as an i8
+               // array which is returned in int regs
+               //
+       case ArgHFA:
+               linfo->ret.storage = LLVMArgFpStruct;
+               linfo->ret.nslots = cinfo->ret.nregs;
+               linfo->ret.esize = cinfo->ret.esize;
+               break;
+       case ArgVtypeInIRegs:
+               /* LLVM models this by returning an int */
+               linfo->ret.storage = LLVMArgVtypeAsScalar;
+               linfo->ret.nslots = cinfo->ret.nregs;
+               linfo->ret.esize = cinfo->ret.esize;
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+
+       for (i = 0; i < n; ++i) {
+               LLVMArgInfo *lainfo = &linfo->args [i];
+
+               ainfo = cinfo->args + i;
+
+               lainfo->storage = LLVMArgNone;
+
+               switch (ainfo->storage) {
+               case ArgInIReg:
+               case ArgInFReg:
+               case ArgInFRegR4:
+               case ArgOnStack:
+               case ArgOnStackR4:
+               case ArgOnStackR8:
+                       lainfo->storage = LLVMArgNormal;
+                       break;
+               case ArgVtypeByRef:
+               case ArgVtypeByRefOnStack:
+                       lainfo->storage = LLVMArgVtypeByRef;
+                       break;
+               case ArgHFA: {
+                       int j;
+
+                       lainfo->storage = LLVMArgAsFpArgs;
+                       lainfo->nslots = ainfo->nregs;
+                       lainfo->esize = ainfo->esize;
+                       for (j = 0; j < ainfo->nregs; ++j)
+                               lainfo->pair_storage [j] = LLVMArgInFPReg;
+                       break;
+               }
+               case ArgVtypeInIRegs:
+                       lainfo->storage = LLVMArgAsIArgs;
+                       lainfo->nslots = ainfo->nregs;
+                       break;
+               case ArgVtypeOnStack:
+                       if (ainfo->hfa) {
+                               int j;
+                               /* Same as above */
+                               lainfo->storage = LLVMArgAsFpArgs;
+                               lainfo->nslots = ainfo->nregs;
+                               lainfo->esize = ainfo->esize;
+                               lainfo->ndummy_fpargs = ainfo->nfregs_to_skip;
+                               for (j = 0; j < ainfo->nregs; ++j)
+                                       lainfo->pair_storage [j] = LLVMArgInFPReg;
+                       } else {
+                               lainfo->storage = LLVMArgAsIArgs;
+                               lainfo->nslots = ainfo->size / 8;
+                       }
+                       break;
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+       }
+
+       return linfo;
+}
+#endif
+
+static void
+add_outarg_reg (MonoCompile *cfg, MonoCallInst *call, ArgStorage storage, int reg, MonoInst *arg)
+{
+       MonoInst *ins;
+
+       switch (storage) {
+       case ArgInIReg:
+               MONO_INST_NEW (cfg, ins, OP_MOVE);
+               ins->dreg = mono_alloc_ireg_copy (cfg, arg->dreg);
+               ins->sreg1 = arg->dreg;
+               MONO_ADD_INS (cfg->cbb, ins);
+               mono_call_inst_add_outarg_reg (cfg, call, ins->dreg, reg, FALSE);
+               break;
+       case ArgInFReg:
+               MONO_INST_NEW (cfg, ins, OP_FMOVE);
+               ins->dreg = mono_alloc_freg (cfg);
+               ins->sreg1 = arg->dreg;
+               MONO_ADD_INS (cfg->cbb, ins);
+               mono_call_inst_add_outarg_reg (cfg, call, ins->dreg, reg, TRUE);
+               break;
+       case ArgInFRegR4:
+               if (COMPILE_LLVM (cfg))
+                       MONO_INST_NEW (cfg, ins, OP_FMOVE);
+               else if (cfg->r4fp)
+                       MONO_INST_NEW (cfg, ins, OP_RMOVE);
+               else
+                       MONO_INST_NEW (cfg, ins, OP_ARM_SETFREG_R4);
+               ins->dreg = mono_alloc_freg (cfg);
+               ins->sreg1 = arg->dreg;
+               MONO_ADD_INS (cfg->cbb, ins);
+               mono_call_inst_add_outarg_reg (cfg, call, ins->dreg, reg, TRUE);
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+}
+
+static void
+emit_sig_cookie (MonoCompile *cfg, MonoCallInst *call, CallInfo *cinfo)
+{
+       MonoMethodSignature *tmp_sig;
+       int sig_reg;
+
+       if (call->tail_call)
+               NOT_IMPLEMENTED;
+
+       g_assert (cinfo->sig_cookie.storage == ArgOnStack);
+                       
+       /*
+        * mono_ArgIterator_Setup assumes the signature cookie is 
+        * passed first and all the arguments which were before it are
+        * passed on the stack after the signature. So compensate by 
+        * passing a different signature.
+        */
+       tmp_sig = mono_metadata_signature_dup (call->signature);
+       tmp_sig->param_count -= call->signature->sentinelpos;
+       tmp_sig->sentinelpos = 0;
+       memcpy (tmp_sig->params, call->signature->params + call->signature->sentinelpos, tmp_sig->param_count * sizeof (MonoType*));
+
+       sig_reg = mono_alloc_ireg (cfg);
+       MONO_EMIT_NEW_SIGNATURECONST (cfg, sig_reg, tmp_sig);
+
+       MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STORE_MEMBASE_REG, ARMREG_SP, cinfo->sig_cookie.offset, sig_reg);
+}
+
+void
+mono_arch_emit_call (MonoCompile *cfg, MonoCallInst *call)
+{
+       MonoMethodSignature *sig;
+       MonoInst *arg, *vtarg;
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
+       int i;
+
+       sig = call->signature;
+
+       cinfo = get_call_info (cfg->mempool, sig);
+
+       switch (cinfo->ret.storage) {
+       case ArgVtypeInIRegs:
+       case ArgHFA:
+               /*
+                * The vtype is returned in registers, save the return area address in a local, and save the vtype into
+                * the location pointed to by it after call in emit_move_return_value ().
+                */
+               if (!cfg->arch.vret_addr_loc) {
+                       cfg->arch.vret_addr_loc = mono_compile_create_var (cfg, &mono_defaults.int_class->byval_arg, OP_LOCAL);
+                       /* Prevent it from being register allocated or optimized away */
+                       ((MonoInst*)cfg->arch.vret_addr_loc)->flags |= MONO_INST_VOLATILE;
+               }
+
+               MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, ((MonoInst*)cfg->arch.vret_addr_loc)->dreg, call->vret_var->dreg);
+               break;
+       case ArgVtypeByRef:
+               /* Pass the vtype return address in R8 */
+               MONO_INST_NEW (cfg, vtarg, OP_MOVE);
+               vtarg->sreg1 = call->vret_var->dreg;
+               vtarg->dreg = mono_alloc_preg (cfg);
+               MONO_ADD_INS (cfg->cbb, vtarg);
+
+               mono_call_inst_add_outarg_reg (cfg, call, vtarg->dreg, cinfo->ret.reg, FALSE);
+               break;
+       default:
+               break;
+       }
+
+       for (i = 0; i < cinfo->nargs; ++i) {
+               ainfo = cinfo->args + i;
+               arg = call->args [i];
+
+               if ((sig->call_convention == MONO_CALL_VARARG) && (i == sig->sentinelpos)) {
+                       /* Emit the signature cookie just before the implicit arguments */
+                       emit_sig_cookie (cfg, call, cinfo);
+               }
+
+               switch (ainfo->storage) {
+               case ArgInIReg:
+               case ArgInFReg:
+               case ArgInFRegR4:
+                       add_outarg_reg (cfg, call, ainfo->storage, ainfo->reg, arg);
+                       break;
+               case ArgOnStack:
+                       switch (ainfo->slot_size) {
+                       case 8:
+                               MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STORE_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                               break;
+                       case 4:
+                               MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI4_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                               break;
+                       case 2:
+                               MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI2_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                               break;
+                       case 1:
+                               MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI1_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                               break;
+                       }
+                       break;
+               case ArgOnStackR8:
+                       MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STORER8_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                       break;
+               case ArgOnStackR4:
+                       MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STORER4_MEMBASE_REG, ARMREG_SP, ainfo->offset, arg->dreg);
+                       break;
+               case ArgVtypeInIRegs:
+               case ArgVtypeByRef:
+               case ArgVtypeByRefOnStack:
+               case ArgVtypeOnStack:
+               case ArgHFA: {
+                       MonoInst *ins;
+                       guint32 align;
+                       guint32 size;
+
+                       size = mono_class_value_size (arg->klass, &align);
+
+                       MONO_INST_NEW (cfg, ins, OP_OUTARG_VT);
+                       ins->sreg1 = arg->dreg;
+                       ins->klass = arg->klass;
+                       ins->backend.size = size;
+                       ins->inst_p0 = call;
+                       ins->inst_p1 = mono_mempool_alloc (cfg->mempool, sizeof (ArgInfo));
+                       memcpy (ins->inst_p1, ainfo, sizeof (ArgInfo));
+                       MONO_ADD_INS (cfg->cbb, ins);
+                       break;
+               }
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+       }
+
+       /* Handle the case where there are no implicit arguments */
+       if (!sig->pinvoke && (sig->call_convention == MONO_CALL_VARARG) && (cinfo->nargs == sig->sentinelpos))
+               emit_sig_cookie (cfg, call, cinfo);
+
+       call->call_info = cinfo;
+       call->stack_usage = cinfo->stack_usage;
+}
+
+void
+mono_arch_emit_outarg_vt (MonoCompile *cfg, MonoInst *ins, MonoInst *src)
+{
+       MonoCallInst *call = (MonoCallInst*)ins->inst_p0;
+       ArgInfo *ainfo = ins->inst_p1;
+       MonoInst *load;
+       int i;
+
+       if (ins->backend.size == 0 && !ainfo->gsharedvt)
+               return;
+
+       switch (ainfo->storage) {
+       case ArgVtypeInIRegs:
+               for (i = 0; i < ainfo->nregs; ++i) {
+                       // FIXME: Smaller sizes
+                       MONO_INST_NEW (cfg, load, OP_LOADI8_MEMBASE);
+                       load->dreg = mono_alloc_ireg (cfg);
+                       load->inst_basereg = src->dreg;
+                       load->inst_offset = i * sizeof(mgreg_t);
+                       MONO_ADD_INS (cfg->cbb, load);
+                       add_outarg_reg (cfg, call, ArgInIReg, ainfo->reg + i, load);
+               }
+               break;
+       case ArgHFA:
+               for (i = 0; i < ainfo->nregs; ++i) {
+                       if (ainfo->esize == 4)
+                               MONO_INST_NEW (cfg, load, OP_LOADR4_MEMBASE);
+                       else
+                               MONO_INST_NEW (cfg, load, OP_LOADR8_MEMBASE);
+                       load->dreg = mono_alloc_freg (cfg);
+                       load->inst_basereg = src->dreg;
+                       load->inst_offset = ainfo->foffsets [i];
+                       MONO_ADD_INS (cfg->cbb, load);
+                       add_outarg_reg (cfg, call, ainfo->esize == 4 ? ArgInFRegR4 : ArgInFReg, ainfo->reg + i, load);
+               }
+               break;
+       case ArgVtypeByRef:
+       case ArgVtypeByRefOnStack: {
+               MonoInst *vtaddr, *load, *arg;
+
+               /* Pass the vtype address in a reg/on the stack */
+               if (ainfo->gsharedvt) {
+                       load = src;
+               } else {
+                       /* Make a copy of the argument */
+                       vtaddr = mono_compile_create_var (cfg, &ins->klass->byval_arg, OP_LOCAL);
+
+                       MONO_INST_NEW (cfg, load, OP_LDADDR);
+                       load->inst_p0 = vtaddr;
+                       vtaddr->flags |= MONO_INST_INDIRECT;
+                       load->type = STACK_MP;
+                       load->klass = vtaddr->klass;
+                       load->dreg = mono_alloc_ireg (cfg);
+                       MONO_ADD_INS (cfg->cbb, load);
+                       mini_emit_memcpy (cfg, load->dreg, 0, src->dreg, 0, ainfo->size, 8);
+               }
+
+               if (ainfo->storage == ArgVtypeByRef) {
+                       MONO_INST_NEW (cfg, arg, OP_MOVE);
+                       arg->dreg = mono_alloc_preg (cfg);
+                       arg->sreg1 = load->dreg;
+                       MONO_ADD_INS (cfg->cbb, arg);
+                       add_outarg_reg (cfg, call, ArgInIReg, ainfo->reg, arg);
+               } else {
+                       MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STORE_MEMBASE_REG, ARMREG_SP, ainfo->offset, load->dreg);
+               }
+               break;
+       }
+       case ArgVtypeOnStack:
+               for (i = 0; i < ainfo->size / 8; ++i) {
+                       MONO_INST_NEW (cfg, load, OP_LOADI8_MEMBASE);
+                       load->dreg = mono_alloc_ireg (cfg);
+                       load->inst_basereg = src->dreg;
+                       load->inst_offset = i * 8;
+                       MONO_ADD_INS (cfg->cbb, load);
+                       MONO_EMIT_NEW_STORE_MEMBASE (cfg, OP_STOREI8_MEMBASE_REG, ARMREG_SP, ainfo->offset + (i * 8), load->dreg);
+               }
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+}
+
+void
+mono_arch_emit_setret (MonoCompile *cfg, MonoMethod *method, MonoInst *val)
+{
+       MonoMethodSignature *sig;
+       CallInfo *cinfo;
+
+       sig = mono_method_signature (cfg->method);
+       if (!cfg->arch.cinfo)
+               cfg->arch.cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = cfg->arch.cinfo;
+
+       switch (cinfo->ret.storage) {
+       case ArgNone:
+               break;
+       case ArgInIReg:
+               MONO_EMIT_NEW_UNALU (cfg, OP_MOVE, cfg->ret->dreg, val->dreg);
+               break;
+       case ArgInFReg:
+               MONO_EMIT_NEW_UNALU (cfg, OP_FMOVE, cfg->ret->dreg, val->dreg);
+               break;
+       case ArgInFRegR4:
+               if (COMPILE_LLVM (cfg))
+                       MONO_EMIT_NEW_UNALU (cfg, OP_FMOVE, cfg->ret->dreg, val->dreg);
+               else if (cfg->r4fp)
+                       MONO_EMIT_NEW_UNALU (cfg, OP_RMOVE, cfg->ret->dreg, val->dreg);
+               else
+                       MONO_EMIT_NEW_UNALU (cfg, OP_ARM_SETFREG_R4, cfg->ret->dreg, val->dreg);
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+}
+
+gboolean
+mono_arch_tail_call_supported (MonoCompile *cfg, MonoMethodSignature *caller_sig, MonoMethodSignature *callee_sig)
+{
+       CallInfo *c1, *c2;
+       gboolean res;
+
+       if (cfg->compile_aot && !cfg->full_aot)
+               /* OP_TAILCALL doesn't work with AOT */
+               return FALSE;
+
+       c1 = get_call_info (NULL, caller_sig);
+       c2 = get_call_info (NULL, callee_sig);
+       res = TRUE;
+       // FIXME: Relax these restrictions
+       if (c1->stack_usage != 0)
+               res = FALSE;
+       if (c1->stack_usage != c2->stack_usage)
+               res = FALSE;
+       if ((c1->ret.storage != ArgNone && c1->ret.storage != ArgInIReg) || c1->ret.storage != c2->ret.storage)
+               res = FALSE;
+
+       g_free (c1);
+       g_free (c2);
+
+       return res;
+}
+
+gboolean 
+mono_arch_is_inst_imm (gint64 imm)
+{
+       return (imm >= -((gint64)1<<31) && imm <= (((gint64)1<<31)-1));
+}
+
+void*
+mono_arch_instrument_prolog (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments)
+{
+       NOT_IMPLEMENTED;
+       return NULL;
+}
+
+void*
+mono_arch_instrument_epilog_full (MonoCompile *cfg, void *func, void *p, gboolean enable_arguments, gboolean preserve_argument_registers)
+{
+       NOT_IMPLEMENTED;
+       return NULL;
+}
+
+void
+mono_arch_peephole_pass_1 (MonoCompile *cfg, MonoBasicBlock *bb)
+{
+       //NOT_IMPLEMENTED;
+}
+
+void
+mono_arch_peephole_pass_2 (MonoCompile *cfg, MonoBasicBlock *bb)
+{
+       //NOT_IMPLEMENTED;
+}
+
+#define ADD_NEW_INS(cfg,dest,op) do {       \
+               MONO_INST_NEW ((cfg), (dest), (op)); \
+        mono_bblock_insert_before_ins (bb, ins, (dest)); \
+       } while (0)
+
+void
+mono_arch_lowering_pass (MonoCompile *cfg, MonoBasicBlock *bb)
+{
+       MonoInst *ins, *temp, *last_ins = NULL;
+
+       MONO_BB_FOR_EACH_INS (bb, ins) {
+               switch (ins->opcode) {
+               case OP_SBB:
+               case OP_ISBB:
+               case OP_SUBCC:
+               case OP_ISUBCC:
+                       if (ins->next  && (ins->next->opcode == OP_COND_EXC_C || ins->next->opcode == OP_COND_EXC_IC))
+                               /* ARM sets the C flag to 1 if there was _no_ overflow */
+                               ins->next->opcode = OP_COND_EXC_NC;
+                       break;
+               case OP_IDIV_IMM:
+               case OP_IREM_IMM:
+               case OP_IDIV_UN_IMM:
+               case OP_IREM_UN_IMM:
+               case OP_LREM_IMM:
+                       mono_decompose_op_imm (cfg, bb, ins);
+                       break;
+               case OP_LOCALLOC_IMM:
+                       if (ins->inst_imm > 32) {
+                               ADD_NEW_INS (cfg, temp, OP_ICONST);
+                               temp->inst_c0 = ins->inst_imm;
+                               temp->dreg = mono_alloc_ireg (cfg);
+                               ins->sreg1 = temp->dreg;
+                               ins->opcode = mono_op_imm_to_op (ins->opcode);
+                       }
+                       break;
+               case OP_ICOMPARE_IMM:
+                       if (ins->inst_imm == 0 && ins->next && ins->next->opcode == OP_IBEQ) {
+                               ins->next->opcode = OP_ARM64_CBZW;
+                               ins->next->sreg1 = ins->sreg1;
+                               NULLIFY_INS (ins);
+                       } else if (ins->inst_imm == 0 && ins->next && ins->next->opcode == OP_IBNE_UN) {
+                               ins->next->opcode = OP_ARM64_CBNZW;
+                               ins->next->sreg1 = ins->sreg1;
+                               NULLIFY_INS (ins);
+                       }
+                       break;
+               case OP_LCOMPARE_IMM:
+               case OP_COMPARE_IMM:
+                       if (ins->inst_imm == 0 && ins->next && ins->next->opcode == OP_LBEQ) {
+                               ins->next->opcode = OP_ARM64_CBZX;
+                               ins->next->sreg1 = ins->sreg1;
+                               NULLIFY_INS (ins);
+                       } else if (ins->inst_imm == 0 && ins->next && ins->next->opcode == OP_LBNE_UN) {
+                               ins->next->opcode = OP_ARM64_CBNZX;
+                               ins->next->sreg1 = ins->sreg1;
+                               NULLIFY_INS (ins);
+                       }
+                       break;
+               case OP_FCOMPARE: {
+                       gboolean swap = FALSE;
+                       int reg;
+
+                       if (!ins->next) {
+                               /* Optimized away */
+                               NULLIFY_INS (ins);
+                               break;
+                       }
+
+                       /*
+                        * FP compares with unordered operands set the flags
+                        * to NZCV=0011, which matches some non-unordered compares
+                        * as well, like LE, so have to swap the operands.
+                        */
+                       switch (ins->next->opcode) {
+                       case OP_FBLT:
+                               ins->next->opcode = OP_FBGT;
+                               swap = TRUE;
+                               break;
+                       case OP_FBLE:
+                               ins->next->opcode = OP_FBGE;
+                               swap = TRUE;
+                               break;
+                       default:
+                               break;
+                       }
+                       if (swap) {
+                               reg = ins->sreg1;
+                               ins->sreg1 = ins->sreg2;
+                               ins->sreg2 = reg;
+                       }
+                       break;
+               }
+               default:
+                       break;
+               }
+
+               last_ins = ins;
+       }
+       bb->last_ins = last_ins;
+       bb->max_vreg = cfg->next_vreg;
+}
+
+void
+mono_arch_decompose_long_opts (MonoCompile *cfg, MonoInst *long_ins)
+{
+}
+
+static int
+opcode_to_armcond (int opcode)
+{
+       switch (opcode) {
+       case OP_IBEQ:
+       case OP_LBEQ:
+       case OP_FBEQ:
+       case OP_CEQ:
+       case OP_ICEQ:
+       case OP_LCEQ:
+       case OP_FCEQ:
+       case OP_RCEQ:
+       case OP_COND_EXC_IEQ:
+       case OP_COND_EXC_EQ:
+               return ARMCOND_EQ;
+       case OP_IBGE:
+       case OP_LBGE:
+       case OP_FBGE:
+       case OP_ICGE:
+       case OP_FCGE:
+       case OP_RCGE:
+               return ARMCOND_GE;
+       case OP_IBGT:
+       case OP_LBGT:
+       case OP_FBGT:
+       case OP_CGT:
+       case OP_ICGT:
+       case OP_LCGT:
+       case OP_FCGT:
+       case OP_RCGT:
+       case OP_COND_EXC_IGT:
+       case OP_COND_EXC_GT:
+               return ARMCOND_GT;
+       case OP_IBLE:
+       case OP_LBLE:
+       case OP_FBLE:
+       case OP_ICLE:
+       case OP_FCLE:
+       case OP_RCLE:
+               return ARMCOND_LE;
+       case OP_IBLT:
+       case OP_LBLT:
+       case OP_FBLT:
+       case OP_CLT:
+       case OP_ICLT:
+       case OP_LCLT:
+       case OP_COND_EXC_ILT:
+       case OP_COND_EXC_LT:
+               return ARMCOND_LT;
+       case OP_IBNE_UN:
+       case OP_LBNE_UN:
+       case OP_FBNE_UN:
+       case OP_ICNEQ:
+       case OP_FCNEQ:
+       case OP_RCNEQ:
+       case OP_COND_EXC_INE_UN:
+       case OP_COND_EXC_NE_UN:
+               return ARMCOND_NE;
+       case OP_IBGE_UN:
+       case OP_LBGE_UN:
+       case OP_FBGE_UN:
+       case OP_ICGE_UN:
+       case OP_COND_EXC_IGE_UN:
+       case OP_COND_EXC_GE_UN:
+               return ARMCOND_HS;
+       case OP_IBGT_UN:
+       case OP_LBGT_UN:
+       case OP_FBGT_UN:
+       case OP_CGT_UN:
+       case OP_ICGT_UN:
+       case OP_LCGT_UN:
+       case OP_FCGT_UN:
+       case OP_RCGT_UN:
+       case OP_COND_EXC_IGT_UN:
+       case OP_COND_EXC_GT_UN:
+               return ARMCOND_HI;
+       case OP_IBLE_UN:
+       case OP_LBLE_UN:
+       case OP_FBLE_UN:
+       case OP_ICLE_UN:
+       case OP_COND_EXC_ILE_UN:
+       case OP_COND_EXC_LE_UN:
+               return ARMCOND_LS;
+       case OP_IBLT_UN:
+       case OP_LBLT_UN:
+       case OP_FBLT_UN:
+       case OP_CLT_UN:
+       case OP_ICLT_UN:
+       case OP_LCLT_UN:
+       case OP_COND_EXC_ILT_UN:
+       case OP_COND_EXC_LT_UN:
+               return ARMCOND_LO;
+               /*
+                * FCMP sets the NZCV condition bits as follows:
+                * eq = 0110
+                * < = 1000
+                * > = 0010
+                * unordered = 0011
+                * ARMCOND_LT is N!=V, so it matches unordered too, so
+                * fclt and fclt_un need to be special cased.
+                */
+       case OP_FCLT:
+       case OP_RCLT:
+               /* N==1 */
+               return ARMCOND_MI;
+       case OP_FCLT_UN:
+       case OP_RCLT_UN:
+               return ARMCOND_LT;
+       case OP_COND_EXC_C:
+       case OP_COND_EXC_IC:
+               return ARMCOND_CS;
+       case OP_COND_EXC_OV:
+       case OP_COND_EXC_IOV:
+               return ARMCOND_VS;
+       case OP_COND_EXC_NC:
+       case OP_COND_EXC_INC:
+               return ARMCOND_CC;
+       case OP_COND_EXC_NO:
+       case OP_COND_EXC_INO:
+               return ARMCOND_VC;
+       default:
+               printf ("%s\n", mono_inst_name (opcode));
+               g_assert_not_reached ();
+               return -1;
+       }
+}
+
+/* This clobbers LR */
+static inline __attribute__((warn_unused_result)) guint8*
+emit_cond_exc (MonoCompile *cfg, guint8 *code, int opcode, const char *exc_name)
+{
+       int cond;
+
+       cond = opcode_to_armcond (opcode);
+       /* Capture PC */
+       arm_adrx (code, ARMREG_IP1, code);
+       mono_add_patch_info_rel (cfg, code - cfg->native_code, MONO_PATCH_INFO_EXC, exc_name, MONO_R_ARM64_BCC);
+       arm_bcc (code, cond, 0);
+       return code;
+}
+
+static guint8*
+emit_move_return_value (MonoCompile *cfg, guint8 * code, MonoInst *ins)
+{
+       CallInfo *cinfo;
+       MonoCallInst *call;
+
+       call = (MonoCallInst*)ins;
+       cinfo = call->call_info;
+       g_assert (cinfo);
+       switch (cinfo->ret.storage) {
+       case ArgNone:
+               break;
+       case ArgInIReg:
+               /* LLVM compiled code might only set the bottom bits */
+               if (call->signature && mini_get_underlying_type (call->signature->ret)->type == MONO_TYPE_I4)
+                       arm_sxtwx (code, call->inst.dreg, cinfo->ret.reg);
+               else if (call->inst.dreg != cinfo->ret.reg)
+                       arm_movx (code, call->inst.dreg, cinfo->ret.reg);
+               break;
+       case ArgInFReg:
+               if (call->inst.dreg != cinfo->ret.reg)
+                       arm_fmovd (code, call->inst.dreg, cinfo->ret.reg);
+               break;
+       case ArgInFRegR4:
+               if (cfg->r4fp)
+                       arm_fmovs (code, call->inst.dreg, cinfo->ret.reg);
+               else
+                       arm_fcvt_sd (code, call->inst.dreg, cinfo->ret.reg);
+               break;
+       case ArgVtypeInIRegs: {
+               MonoInst *loc = cfg->arch.vret_addr_loc;
+               int i;
+
+               /* Load the destination address */
+               g_assert (loc && loc->opcode == OP_REGOFFSET);
+               code = emit_ldrx (code, ARMREG_LR, loc->inst_basereg, loc->inst_offset);
+               for (i = 0; i < cinfo->ret.nregs; ++i)
+                       arm_strx (code, cinfo->ret.reg + i, ARMREG_LR, i * 8);
+               break;
+       }
+       case ArgHFA: {
+               MonoInst *loc = cfg->arch.vret_addr_loc;
+               int i;
+
+               /* Load the destination address */
+               g_assert (loc && loc->opcode == OP_REGOFFSET);
+               code = emit_ldrx (code, ARMREG_LR, loc->inst_basereg, loc->inst_offset);
+               for (i = 0; i < cinfo->ret.nregs; ++i) {
+                       if (cinfo->ret.esize == 4)
+                               arm_strfpw (code, cinfo->ret.reg + i, ARMREG_LR, cinfo->ret.foffsets [i]);
+                       else
+                               arm_strfpx (code, cinfo->ret.reg + i, ARMREG_LR, cinfo->ret.foffsets [i]);
+               }
+               break;
+       }
+       case ArgVtypeByRef:
+               break;
+       default:
+               g_assert_not_reached ();
+               break;
+       }
+       return code;
+}
+
+/*
+ * emit_branch_island:
+ *
+ *   Emit a branch island for the conditional branches from cfg->native_code + start_offset to code.
+ */
+static guint8*
+emit_branch_island (MonoCompile *cfg, guint8 *code, int start_offset)
+{
+       MonoJumpInfo *ji;
+       int offset, island_size;
+
+       /* Iterate over the patch infos added so far by this bb */
+       island_size = 0;
+       for (ji = cfg->patch_info; ji; ji = ji->next) {
+               if (ji->ip.i < start_offset)
+                       /* The patch infos are in reverse order, so this means the end */
+                       break;
+               if (ji->relocation == MONO_R_ARM64_BCC || ji->relocation == MONO_R_ARM64_CBZ)
+                       island_size += 4;
+       }
+
+       if (island_size) {
+               offset = code - cfg->native_code;
+               if (offset > (cfg->code_size - island_size - 16)) {
+                       cfg->code_size *= 2;
+                       cfg->native_code = g_realloc (cfg->native_code, cfg->code_size);
+                       code = cfg->native_code + offset;
+               }
+
+               /* Branch over the island */
+               arm_b (code, code + 4 + island_size);
+
+               for (ji = cfg->patch_info; ji; ji = ji->next) {
+                       if (ji->ip.i < start_offset)
+                               break;
+                       if (ji->relocation == MONO_R_ARM64_BCC || ji->relocation == MONO_R_ARM64_CBZ) {
+                               /* Rewrite the cond branch so it branches to an uncoditional branch in the branch island */
+                               arm_patch_rel (cfg->native_code + ji->ip.i, code, ji->relocation);
+                               /* Rewrite the patch so it points to the unconditional branch */
+                               ji->ip.i = code - cfg->native_code;
+                               ji->relocation = MONO_R_ARM64_B;
+                               arm_b (code, code);
+                       }
+               }
+       }
+       return code;
+}
+
+void
+mono_arch_output_basic_block (MonoCompile *cfg, MonoBasicBlock *bb)
+{
+       MonoInst *ins;
+       MonoCallInst *call;
+       guint offset;
+       guint8 *code = cfg->native_code + cfg->code_len;
+       int start_offset, max_len, dreg, sreg1, sreg2;
+       mgreg_t imm;
+
+       if (cfg->verbose_level > 2)
+               g_print ("Basic block %d starting at offset 0x%x\n", bb->block_num, bb->native_offset);
+
+       start_offset = code - cfg->native_code;
+
+       MONO_BB_FOR_EACH_INS (bb, ins) {
+               offset = code - cfg->native_code;
+
+               max_len = ((guint8 *)ins_get_spec (ins->opcode))[MONO_INST_LEN];
+
+               if (offset > (cfg->code_size - max_len - 16)) {
+                       cfg->code_size *= 2;
+                       cfg->native_code = g_realloc (cfg->native_code, cfg->code_size);
+                       code = cfg->native_code + offset;
+               }
+
+               if (G_UNLIKELY (cfg->arch.cond_branch_islands && offset - start_offset > 4 * 0x1ffff)) {
+                       /* Emit a branch island for large basic blocks */
+                       code = emit_branch_island (cfg, code, start_offset);
+                       offset = code - cfg->native_code;
+                       start_offset = offset;
+               }
+
+               mono_debug_record_line_number (cfg, ins, offset);
+
+               dreg = ins->dreg;
+               sreg1 = ins->sreg1;
+               sreg2 = ins->sreg2;
+               imm = ins->inst_imm;
+
+               switch (ins->opcode) {
+               case OP_ICONST:
+                       code = emit_imm (code, dreg, ins->inst_c0);
+                       break;
+               case OP_I8CONST:
+                       code = emit_imm64 (code, dreg, ins->inst_c0);
+                       break;
+               case OP_MOVE:
+                       if (dreg != sreg1)
+                               arm_movx (code, dreg, sreg1);
+                       break;
+               case OP_NOP:
+               case OP_RELAXED_NOP:
+                       break;
+               case OP_JUMP_TABLE:
+                       mono_add_patch_info_rel (cfg, offset, (MonoJumpInfoType)ins->inst_i1, ins->inst_p0, MONO_R_ARM64_IMM);
+                       code = emit_imm64_template (code, dreg);
+                       break;
+               case OP_BREAK:
+                       /*
+                        * gdb does not like encountering the hw breakpoint ins in the debugged code. 
+                        * So instead of emitting a trap, we emit a call a C function and place a 
+                        * breakpoint there.
+                        */
+                       code = emit_call (cfg, code, MONO_PATCH_INFO_INTERNAL_METHOD, (gpointer)"mono_break");
+                       break;
+               case OP_LOCALLOC: {
+                       guint8 *buf [16];
+
+                       arm_addx_imm (code, ARMREG_IP0, sreg1, (MONO_ARCH_FRAME_ALIGNMENT - 1));
+                       // FIXME: andx_imm doesn't work yet
+                       code = emit_imm (code, ARMREG_IP1, -MONO_ARCH_FRAME_ALIGNMENT);
+                       arm_andx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+                       //arm_andx_imm (code, ARMREG_IP0, sreg1, - MONO_ARCH_FRAME_ALIGNMENT);
+                       arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+                       arm_subx (code, ARMREG_IP1, ARMREG_IP1, ARMREG_IP0);
+                       arm_movspx (code, ARMREG_SP, ARMREG_IP1);
+
+                       /* Init */
+                       /* ip1 = pointer, ip0 = end */
+                       arm_addx (code, ARMREG_IP0, ARMREG_IP1, ARMREG_IP0);
+                       buf [0] = code;
+                       arm_cmpx (code, ARMREG_IP1, ARMREG_IP0);
+                       buf [1] = code;
+                       arm_bcc (code, ARMCOND_EQ, 0);
+                       arm_stpx (code, ARMREG_RZR, ARMREG_RZR, ARMREG_IP1, 0);
+                       arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, 16);
+                       arm_b (code, buf [0]);
+                       arm_patch_rel (buf [1], code, MONO_R_ARM64_BCC);
+
+                       arm_movspx (code, dreg, ARMREG_SP);
+                       if (cfg->param_area)
+                               code = emit_subx_sp_imm (code, cfg->param_area);
+                       break;
+               }
+               case OP_LOCALLOC_IMM: {
+                       int imm, offset;
+
+                       imm = ALIGN_TO (ins->inst_imm, MONO_ARCH_FRAME_ALIGNMENT);
+                       g_assert (arm_is_arith_imm (imm));
+                       arm_subx_imm (code, ARMREG_SP, ARMREG_SP, imm);
+
+                       /* Init */
+                       g_assert (MONO_ARCH_FRAME_ALIGNMENT == 16);
+                       offset = 0;
+                       while (offset < imm) {
+                               arm_stpx (code, ARMREG_RZR, ARMREG_RZR, ARMREG_SP, offset);
+                               offset += 16;
+                       }
+                       arm_movspx (code, dreg, ARMREG_SP);
+                       if (cfg->param_area)
+                               code = emit_subx_sp_imm (code, cfg->param_area);
+                       break;
+               }
+               case OP_AOTCONST:
+                       code = emit_aotconst (cfg, code, dreg, (MonoJumpInfoType)ins->inst_i1, ins->inst_p0);
+                       break;
+               case OP_OBJC_GET_SELECTOR:
+                       mono_add_patch_info (cfg, offset, MONO_PATCH_INFO_OBJC_SELECTOR_REF, ins->inst_p0);
+                       /* See arch_emit_objc_selector_ref () in aot-compiler.c */
+                       arm_ldrx_lit (code, ins->dreg, 0);
+                       arm_nop (code);
+                       arm_nop (code);
+                       break;
+               case OP_SEQ_POINT: {
+                       MonoInst *info_var = cfg->arch.seq_point_info_var;
+
+                       /*
+                        * For AOT, we use one got slot per method, which will point to a
+                        * SeqPointInfo structure, containing all the information required
+                        * by the code below.
+                        */
+                       if (cfg->compile_aot) {
+                               g_assert (info_var);
+                               g_assert (info_var->opcode == OP_REGOFFSET);
+                       }
+
+                       if (ins->flags & MONO_INST_SINGLE_STEP_LOC) {
+                               MonoInst *var = cfg->arch.ss_tramp_var;
+
+                               g_assert (var);
+                               g_assert (var->opcode == OP_REGOFFSET);
+                               /* Load ss_tramp_var */
+                               /* This is equal to &ss_trampoline */
+                               arm_ldrx (code, ARMREG_IP1, var->inst_basereg, var->inst_offset);
+                               /* Load the trampoline address */
+                               arm_ldrx (code, ARMREG_IP1, ARMREG_IP1, 0);
+                               /* Call it if it is non-null */
+                               arm_cbzx (code, ARMREG_IP1, code + 8);
+                               arm_blrx (code, ARMREG_IP1);
+                       }
+
+                       mono_add_seq_point (cfg, bb, ins, code - cfg->native_code);
+
+                       if (cfg->compile_aot) {
+                               guint32 offset = code - cfg->native_code;
+                               guint32 val;
+
+                               arm_ldrx (code, ARMREG_IP1, info_var->inst_basereg, info_var->inst_offset);
+                               /* Add the offset */
+                               val = ((offset / 4) * sizeof (guint8*)) + MONO_STRUCT_OFFSET (SeqPointInfo, bp_addrs);
+                               /* Load the info->bp_addrs [offset], which is either 0 or the address of the bp trampoline */
+                               code = emit_ldrx (code, ARMREG_IP1, ARMREG_IP1, val);
+                               /* Skip the load if its 0 */
+                               arm_cbzx (code, ARMREG_IP1, code + 8);
+                               /* Call the breakpoint trampoline */
+                               arm_blrx (code, ARMREG_IP1);
+                       } else {
+                               MonoInst *var = cfg->arch.bp_tramp_var;
+
+                               g_assert (var);
+                               g_assert (var->opcode == OP_REGOFFSET);
+                               /* Load the address of the bp trampoline into IP0 */
+                               arm_ldrx (code, ARMREG_IP0, var->inst_basereg, var->inst_offset);
+                               /* 
+                                * A placeholder for a possible breakpoint inserted by
+                                * mono_arch_set_breakpoint ().
+                                */
+                               arm_nop (code);
+                       }
+                       break;
+               }
+
+                       /* BRANCH */
+               case OP_BR:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_target_bb, MONO_R_ARM64_B);
+                       arm_b (code, code);
+                       break;
+               case OP_BR_REG:
+                       arm_brx (code, sreg1);
+                       break;
+               case OP_IBEQ:
+               case OP_IBGE:
+               case OP_IBGT:
+               case OP_IBLE:
+               case OP_IBLT:
+               case OP_IBNE_UN:
+               case OP_IBGE_UN:
+               case OP_IBGT_UN:
+               case OP_IBLE_UN:
+               case OP_IBLT_UN:
+               case OP_LBEQ:
+               case OP_LBGE:
+               case OP_LBGT:
+               case OP_LBLE:
+               case OP_LBLT:
+               case OP_LBNE_UN:
+               case OP_LBGE_UN:
+               case OP_LBGT_UN:
+               case OP_LBLE_UN:
+               case OP_LBLT_UN:
+               case OP_FBEQ:
+               case OP_FBNE_UN:
+               case OP_FBLT:
+               case OP_FBGT:
+               case OP_FBGT_UN:
+               case OP_FBLE:
+               case OP_FBGE:
+               case OP_FBGE_UN: {
+                       int cond;
+
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_BCC);
+                       cond = opcode_to_armcond (ins->opcode);
+                       arm_bcc (code, cond, 0);
+                       break;
+               }
+               case OP_FBLT_UN:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_BCC);
+                       /* For fp compares, ARMCOND_LT is lt or unordered */
+                       arm_bcc (code, ARMCOND_LT, 0);
+                       break;
+               case OP_FBLE_UN:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_BCC);
+                       arm_bcc (code, ARMCOND_EQ, 0);
+                       offset = code - cfg->native_code;
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_BCC);
+                       /* For fp compares, ARMCOND_LT is lt or unordered */
+                       arm_bcc (code, ARMCOND_LT, 0);
+                       break;
+               case OP_ARM64_CBZW:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_CBZ);
+                       arm_cbzw (code, sreg1, 0);
+                       break;
+               case OP_ARM64_CBZX:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_CBZ);
+                       arm_cbzx (code, sreg1, 0);
+                       break;
+               case OP_ARM64_CBNZW:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_CBZ);
+                       arm_cbnzw (code, sreg1, 0);
+                       break;
+               case OP_ARM64_CBNZX:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_true_bb, MONO_R_ARM64_CBZ);
+                       arm_cbnzx (code, sreg1, 0);
+                       break;
+                       /* ALU */
+               case OP_IADD:
+                       arm_addw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LADD:
+                       arm_addx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ISUB:
+                       arm_subw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LSUB:
+                       arm_subx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_IAND:
+                       arm_andw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LAND:
+                       arm_andx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_IOR:
+                       arm_orrw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LOR:
+                       arm_orrx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_IXOR:
+                       arm_eorw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LXOR:
+                       arm_eorx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_INEG:
+                       arm_negw (code, dreg, sreg1);
+                       break;
+               case OP_LNEG:
+                       arm_negx (code, dreg, sreg1);
+                       break;
+               case OP_INOT:
+                       arm_mvnw (code, dreg, sreg1);
+                       break;
+               case OP_LNOT:
+                       arm_mvnx (code, dreg, sreg1);
+                       break;
+               case OP_IADDCC:
+                       arm_addsw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ADDCC:
+               case OP_LADDCC:
+                       arm_addsx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ISUBCC:
+                       arm_subsw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LSUBCC:
+               case OP_SUBCC:
+                       arm_subsx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ICOMPARE:
+                       arm_cmpw (code, sreg1, sreg2);
+                       break;
+               case OP_COMPARE:
+               case OP_LCOMPARE:
+                       arm_cmpx (code, sreg1, sreg2);
+                       break;
+               case OP_IADD_IMM:
+                       code = emit_addw_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_LADD_IMM:
+               case OP_ADD_IMM:
+                       code = emit_addx_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_ISUB_IMM:
+                       code = emit_subw_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_LSUB_IMM:
+                       code = emit_subx_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_IAND_IMM:
+                       code = emit_andw_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_LAND_IMM:
+               case OP_AND_IMM:
+                       code = emit_andx_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_IOR_IMM:
+                       code = emit_orrw_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_LOR_IMM:
+                       code = emit_orrx_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_IXOR_IMM:
+                       code = emit_eorw_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_LXOR_IMM:
+                       code = emit_eorx_imm (code, dreg, sreg1, imm);
+                       break;
+               case OP_ICOMPARE_IMM:
+                       code = emit_cmpw_imm (code, sreg1, imm);
+                       break;
+               case OP_LCOMPARE_IMM:
+               case OP_COMPARE_IMM:
+                       if (imm == 0) {
+                               arm_cmpx (code, sreg1, ARMREG_RZR);
+                       } else {
+                               // FIXME: 32 vs 64 bit issues for 0xffffffff
+                               code = emit_imm64 (code, ARMREG_LR, imm);
+                               arm_cmpx (code, sreg1, ARMREG_LR);
+                       }
+                       break;
+               case OP_ISHL:
+                       arm_lslvw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LSHL:
+                       arm_lslvx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ISHR:
+                       arm_asrvw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LSHR:
+                       arm_asrvx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ISHR_UN:
+                       arm_lsrvw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LSHR_UN:
+                       arm_lsrvx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_ISHL_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_lslw (code, dreg, sreg1, imm);
+                       break;
+               case OP_LSHL_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_lslx (code, dreg, sreg1, imm);
+                       break;
+               case OP_ISHR_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_asrw (code, dreg, sreg1, imm);
+                       break;
+               case OP_LSHR_IMM:
+               case OP_SHR_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_asrx (code, dreg, sreg1, imm);
+                       break;
+               case OP_ISHR_UN_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_lsrw (code, dreg, sreg1, imm);
+                       break;
+               case OP_SHR_UN_IMM:
+               case OP_LSHR_UN_IMM:
+                       if (imm == 0)
+                               arm_movx (code, dreg, sreg1);
+                       else
+                               arm_lsrx (code, dreg, sreg1, imm);
+                       break;
+
+                       /* 64BIT ALU */
+               case OP_SEXT_I4:
+                       arm_sxtwx (code, dreg, sreg1);
+                       break;
+               case OP_ZEXT_I4:
+                       /* Clean out the upper word */
+                       arm_movw (code, dreg, sreg1);
+                       break;
+               case OP_SHL_IMM:
+                       arm_lslx (code, dreg, sreg1, imm);
+                       break;
+
+                       /* MULTIPLY/DIVISION */
+               case OP_IDIV:
+               case OP_IREM:
+                       // FIXME: Optimize this
+                       /* Check for zero */
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       /* Check for INT_MIN/-1 */
+                       code = emit_imm (code, ARMREG_IP0, 0x80000000);
+                       arm_cmpx (code, sreg1, ARMREG_IP0);
+                       arm_cset (code, ARMCOND_EQ, ARMREG_IP1);
+                       code = emit_imm (code, ARMREG_IP0, 0xffffffff);
+                       arm_cmpx (code, sreg2, ARMREG_IP0);
+                       arm_cset (code, ARMCOND_EQ, ARMREG_IP0);
+                       arm_andx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+                       arm_cmpx_imm (code, ARMREG_IP0, 1);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "OverflowException");
+                       if (ins->opcode == OP_IREM) {
+                               arm_sdivw (code, ARMREG_LR, sreg1, sreg2);
+                               arm_msubw (code, dreg, ARMREG_LR, sreg2, sreg1);
+                       } else {
+                               arm_sdivw (code, dreg, sreg1, sreg2);
+                       }
+                       break;
+               case OP_IDIV_UN:
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       arm_udivw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_IREM_UN:
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       arm_udivw (code, ARMREG_LR, sreg1, sreg2);
+                       arm_msubw (code, dreg, ARMREG_LR, sreg2, sreg1);
+                       break;
+               case OP_LDIV:
+               case OP_LREM:
+                       // FIXME: Optimize this
+                       /* Check for zero */
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       /* Check for INT64_MIN/-1 */
+                       code = emit_imm64 (code, ARMREG_IP0, 0x8000000000000000);
+                       arm_cmpx (code, sreg1, ARMREG_IP0);
+                       arm_cset (code, ARMCOND_EQ, ARMREG_IP1);
+                       code = emit_imm64 (code, ARMREG_IP0, 0xffffffffffffffff);
+                       arm_cmpx (code, sreg2, ARMREG_IP0);
+                       arm_cset (code, ARMCOND_EQ, ARMREG_IP0);
+                       arm_andx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+                       arm_cmpx_imm (code, ARMREG_IP0, 1);
+                       /* 64 bit uses ArithmeticException */
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "ArithmeticException");
+                       if (ins->opcode == OP_LREM) {
+                               arm_sdivx (code, ARMREG_LR, sreg1, sreg2);
+                               arm_msubx (code, dreg, ARMREG_LR, sreg2, sreg1);
+                       } else {
+                               arm_sdivx (code, dreg, sreg1, sreg2);
+                       }
+                       break;
+               case OP_LDIV_UN:
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       arm_udivx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LREM_UN:
+                       arm_cmpx_imm (code, sreg2, 0);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_IEQ, "DivideByZeroException");
+                       arm_udivx (code, ARMREG_LR, sreg1, sreg2);
+                       arm_msubx (code, dreg, ARMREG_LR, sreg2, sreg1);
+                       break;
+               case OP_IMUL:
+                       arm_mulw (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_LMUL:
+                       arm_mulx (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_IMUL_IMM:
+                       code = emit_imm (code, ARMREG_LR, imm);
+                       arm_mulw (code, dreg, sreg1, ARMREG_LR);
+                       break;
+               case OP_MUL_IMM:
+               case OP_LMUL_IMM:
+                       code = emit_imm (code, ARMREG_LR, imm);
+                       arm_mulx (code, dreg, sreg1, ARMREG_LR);
+                       break;
+
+                       /* CONVERSIONS */
+               case OP_ICONV_TO_I1:
+               case OP_LCONV_TO_I1:
+                       arm_sxtbx (code, dreg, sreg1);
+                       break;
+               case OP_ICONV_TO_I2:
+               case OP_LCONV_TO_I2:
+                       arm_sxthx (code, dreg, sreg1);
+                       break;
+               case OP_ICONV_TO_U1:
+               case OP_LCONV_TO_U1:
+                       arm_uxtbw (code, dreg, sreg1);
+                       break;
+               case OP_ICONV_TO_U2:
+               case OP_LCONV_TO_U2:
+                       arm_uxthw (code, dreg, sreg1);
+                       break;
+
+                       /* CSET */
+               case OP_CEQ:
+               case OP_ICEQ:
+               case OP_LCEQ:
+               case OP_CLT:
+               case OP_ICLT:
+               case OP_LCLT:
+               case OP_CGT:
+               case OP_ICGT:
+               case OP_LCGT:
+               case OP_CLT_UN:
+               case OP_ICLT_UN:
+               case OP_LCLT_UN:
+               case OP_CGT_UN:
+               case OP_ICGT_UN:
+               case OP_LCGT_UN:
+               case OP_ICNEQ:
+               case OP_ICGE:
+               case OP_ICLE:
+               case OP_ICGE_UN:
+               case OP_ICLE_UN: {
+                       int cond;
+
+                       cond = opcode_to_armcond (ins->opcode);
+                       arm_cset (code, cond, dreg);
+                       break;
+               }
+               case OP_FCEQ:
+               case OP_FCLT:
+               case OP_FCLT_UN:
+               case OP_FCGT:
+               case OP_FCGT_UN:
+               case OP_FCNEQ:
+               case OP_FCLE:
+               case OP_FCGE: {
+                       int cond;
+
+                       cond = opcode_to_armcond (ins->opcode);
+                       arm_fcmpd (code, sreg1, sreg2);
+                       arm_cset (code, cond, dreg);
+                       break;
+               }
+
+                       /* MEMORY */
+               case OP_LOADI1_MEMBASE:
+                       code = emit_ldrsbx (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADU1_MEMBASE:
+                       code = emit_ldrb (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADI2_MEMBASE:
+                       code = emit_ldrshx (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADU2_MEMBASE:
+                       code = emit_ldrh (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADI4_MEMBASE:
+                       code = emit_ldrswx (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADU4_MEMBASE:
+                       code = emit_ldrw (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOAD_MEMBASE:
+               case OP_LOADI8_MEMBASE:
+                       code = emit_ldrx (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_STOREI1_MEMBASE_IMM:
+               case OP_STOREI2_MEMBASE_IMM:
+               case OP_STOREI4_MEMBASE_IMM:
+               case OP_STORE_MEMBASE_IMM:
+               case OP_STOREI8_MEMBASE_IMM: {
+                       int immreg;
+
+                       if (imm != 0) {
+                               code = emit_imm (code, ARMREG_LR, imm);
+                               immreg = ARMREG_LR;
+                       } else {
+                               immreg = ARMREG_RZR;
+                       }
+
+                       switch (ins->opcode) {
+                       case OP_STOREI1_MEMBASE_IMM:
+                               code = emit_strb (code, immreg, ins->inst_destbasereg, ins->inst_offset);
+                               break;
+                       case OP_STOREI2_MEMBASE_IMM:
+                               code = emit_strh (code, immreg, ins->inst_destbasereg, ins->inst_offset);
+                               break;
+                       case OP_STOREI4_MEMBASE_IMM:
+                               code = emit_strw (code, immreg, ins->inst_destbasereg, ins->inst_offset);
+                               break;
+                       case OP_STORE_MEMBASE_IMM:
+                       case OP_STOREI8_MEMBASE_IMM:
+                               code = emit_strx (code, immreg, ins->inst_destbasereg, ins->inst_offset);
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                               break;
+                       }
+                       break;
+               }
+               case OP_STOREI1_MEMBASE_REG:
+                       code = emit_strb (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       break;
+               case OP_STOREI2_MEMBASE_REG:
+                       code = emit_strh (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       break;
+               case OP_STOREI4_MEMBASE_REG:
+                       code = emit_strw (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       break;
+               case OP_STORE_MEMBASE_REG:
+               case OP_STOREI8_MEMBASE_REG:
+                       code = emit_strx (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       break;
+
+               case OP_TLS_GET:
+                       code = emit_tls_get (code, dreg, ins->inst_offset);
+                       break;
+               case OP_TLS_GET_REG:
+                       code = emit_tls_get_reg (code, dreg, sreg1);
+                       break;
+               case OP_TLS_SET:
+                       code = emit_tls_set (code, sreg1, ins->inst_offset);
+                       break;
+               case OP_TLS_SET_REG:
+                       code = emit_tls_set_reg (code, sreg1, sreg2);
+                       break;
+
+                       /* Atomic */
+               case OP_MEMORY_BARRIER:
+                       arm_dmb (code, 0);
+                       break;
+               case OP_ATOMIC_ADD_I4: {
+                       guint8 *buf [16];
+
+                       buf [0] = code;
+                       arm_ldaxrw (code, ARMREG_IP0, sreg1);
+                       arm_addx (code, ARMREG_IP0, ARMREG_IP0, sreg2);
+                       arm_stlxrw (code, ARMREG_IP1, ARMREG_IP0, sreg1);
+                       arm_cbnzw (code, ARMREG_IP1, buf [0]);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_ADD_I8: {
+                       guint8 *buf [16];
+
+                       buf [0] = code;
+                       arm_ldaxrx (code, ARMREG_IP0, sreg1);
+                       arm_addx (code, ARMREG_IP0, ARMREG_IP0, sreg2);
+                       arm_stlxrx (code, ARMREG_IP1, ARMREG_IP0, sreg1);
+                       arm_cbnzx (code, ARMREG_IP1, buf [0]);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_EXCHANGE_I4: {
+                       guint8 *buf [16];
+
+                       buf [0] = code;
+                       arm_ldaxrw (code, ARMREG_IP0, sreg1);
+                       arm_stlxrw (code, ARMREG_IP1, sreg2, sreg1);
+                       arm_cbnzw (code, ARMREG_IP1, buf [0]);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_EXCHANGE_I8: {
+                       guint8 *buf [16];
+
+                       buf [0] = code;
+                       arm_ldaxrx (code, ARMREG_IP0, sreg1);
+                       arm_stlxrx (code, ARMREG_IP1, sreg2, sreg1);
+                       arm_cbnzw (code, ARMREG_IP1, buf [0]);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_CAS_I4: {
+                       guint8 *buf [16];
+
+                       /* sreg2 is the value, sreg3 is the comparand */
+                       buf [0] = code;
+                       arm_ldaxrw (code, ARMREG_IP0, sreg1);
+                       arm_cmpw (code, ARMREG_IP0, ins->sreg3);
+                       buf [1] = code;
+                       arm_bcc (code, ARMCOND_NE, 0);
+                       arm_stlxrw (code, ARMREG_IP1, sreg2, sreg1);
+                       arm_cbnzw (code, ARMREG_IP1, buf [0]);
+                       arm_patch_rel (buf [1], code, MONO_R_ARM64_BCC);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_CAS_I8: {
+                       guint8 *buf [16];
+
+                       buf [0] = code;
+                       arm_ldaxrx (code, ARMREG_IP0, sreg1);
+                       arm_cmpx (code, ARMREG_IP0, ins->sreg3);
+                       buf [1] = code;
+                       arm_bcc (code, ARMCOND_NE, 0);
+                       arm_stlxrx (code, ARMREG_IP1, sreg2, sreg1);
+                       arm_cbnzw (code, ARMREG_IP1, buf [0]);
+                       arm_patch_rel (buf [1], code, MONO_R_ARM64_BCC);
+
+                       arm_movx (code, dreg, ARMREG_IP0);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_I1: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarb (code, ins->dreg, ARMREG_LR);
+                       arm_sxtbx (code, ins->dreg, ins->dreg);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_U1: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarb (code, ins->dreg, ARMREG_LR);
+                       arm_uxtbx (code, ins->dreg, ins->dreg);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_I2: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarh (code, ins->dreg, ARMREG_LR);
+                       arm_sxthx (code, ins->dreg, ins->dreg);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_U2: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarh (code, ins->dreg, ARMREG_LR);
+                       arm_uxthx (code, ins->dreg, ins->dreg);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_I4: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarw (code, ins->dreg, ARMREG_LR);
+                       arm_sxtwx (code, ins->dreg, ins->dreg);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_U4: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarw (code, ins->dreg, ARMREG_LR);
+                       arm_movw (code, ins->dreg, ins->dreg); /* Clear upper half of the register. */
+                       break;
+               }
+               case OP_ATOMIC_LOAD_I8:
+               case OP_ATOMIC_LOAD_U8: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarx (code, ins->dreg, ARMREG_LR);
+                       break;
+               }
+               case OP_ATOMIC_LOAD_R4: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       if (cfg->r4fp) {
+                               arm_ldarw (code, ARMREG_LR, ARMREG_LR);
+                               arm_fmov_rx_to_double (code, ins->dreg, ARMREG_LR);
+                       } else {
+                               arm_ldarw (code, ARMREG_LR, ARMREG_LR);
+                               arm_fmov_rx_to_double (code, FP_TEMP_REG, ARMREG_LR);
+                               arm_fcvt_sd (code, ins->dreg, FP_TEMP_REG);
+                       }
+                       break;
+               }
+               case OP_ATOMIC_LOAD_R8: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_basereg, ins->inst_offset);
+                       arm_ldarx (code, ARMREG_LR, ARMREG_LR);
+                       arm_fmov_rx_to_double (code, ins->dreg, ARMREG_LR);
+                       break;
+               }
+               case OP_ATOMIC_STORE_I1:
+               case OP_ATOMIC_STORE_U1: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       arm_stlrb (code, ARMREG_LR, ins->sreg1);
+                       break;
+               }
+               case OP_ATOMIC_STORE_I2:
+               case OP_ATOMIC_STORE_U2: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       arm_stlrh (code, ARMREG_LR, ins->sreg1);
+                       break;
+               }
+               case OP_ATOMIC_STORE_I4:
+               case OP_ATOMIC_STORE_U4: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       arm_stlrw (code, ARMREG_LR, ins->sreg1);
+                       break;
+               }
+               case OP_ATOMIC_STORE_I8:
+               case OP_ATOMIC_STORE_U8: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       arm_stlrx (code, ARMREG_LR, ins->sreg1);
+                       break;
+               }
+               case OP_ATOMIC_STORE_R4: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       if (cfg->r4fp) {
+                               arm_fmov_double_to_rx (code, ARMREG_IP0, ins->sreg1);
+                               arm_stlrw (code, ARMREG_LR, ARMREG_IP0);
+                       } else {
+                               arm_fcvt_ds (code, FP_TEMP_REG, ins->sreg1);
+                               arm_fmov_double_to_rx (code, ARMREG_IP0, FP_TEMP_REG);
+                               arm_stlrw (code, ARMREG_LR, ARMREG_IP0);
+                       }
+                       break;
+               }
+               case OP_ATOMIC_STORE_R8: {
+                       code = emit_addx_imm (code, ARMREG_LR, ins->inst_destbasereg, ins->inst_offset);
+                       arm_fmov_double_to_rx (code, ARMREG_IP0, ins->sreg1);
+                       arm_stlrx (code, ARMREG_LR, ARMREG_IP0);
+                       break;
+               }
+
+                       /* FP */
+               case OP_R8CONST: {
+                       guint64 imm = *(guint64*)ins->inst_p0;
+
+                       if (imm == 0) {
+                               arm_fmov_rx_to_double (code, dreg, ARMREG_RZR);
+                       } else {
+                               code = emit_imm64 (code, ARMREG_LR, imm);
+                               arm_fmov_rx_to_double (code, ins->dreg, ARMREG_LR);
+                       }
+                       break;
+               }
+               case OP_R4CONST: {
+                       guint64 imm = *(guint32*)ins->inst_p0;
+
+                       code = emit_imm64 (code, ARMREG_LR, imm);
+                       if (cfg->r4fp) {
+                               arm_fmov_rx_to_double (code, dreg, ARMREG_LR);
+                       } else {
+                               arm_fmov_rx_to_double (code, FP_TEMP_REG, ARMREG_LR);
+                               arm_fcvt_sd (code, dreg, FP_TEMP_REG);
+                       }
+                       break;
+               }
+               case OP_LOADR8_MEMBASE:
+                       code = emit_ldrfpx (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       break;
+               case OP_LOADR4_MEMBASE:
+                       if (cfg->r4fp) {
+                               code = emit_ldrfpw (code, dreg, ins->inst_basereg, ins->inst_offset);
+                       } else {
+                               code = emit_ldrfpw (code, FP_TEMP_REG, ins->inst_basereg, ins->inst_offset);
+                               arm_fcvt_sd (code, dreg, FP_TEMP_REG);
+                       }
+                       break;
+               case OP_STORER8_MEMBASE_REG:
+                       code = emit_strfpx (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       break;
+               case OP_STORER4_MEMBASE_REG:
+                       if (cfg->r4fp) {
+                               code = emit_strfpw (code, sreg1, ins->inst_destbasereg, ins->inst_offset);
+                       } else {
+                               arm_fcvt_ds (code, FP_TEMP_REG, sreg1);
+                               code = emit_strfpw (code, FP_TEMP_REG, ins->inst_destbasereg, ins->inst_offset);
+                       }
+                       break;
+               case OP_FMOVE:
+                       if (dreg != sreg1)
+                               arm_fmovd (code, dreg, sreg1);
+                       break;
+               case OP_RMOVE:
+                       if (dreg != sreg1)
+                               arm_fmovs (code, dreg, sreg1);
+                       break;
+               case OP_MOVE_F_TO_I4:
+                       if (cfg->r4fp) {
+                               arm_fmov_double_to_rx (code, ins->dreg, ins->sreg1);
+                       } else {
+                               arm_fcvt_ds (code, ins->dreg, ins->sreg1);
+                               arm_fmov_double_to_rx (code, ins->dreg, ins->dreg);
+                       }
+                       break;
+               case OP_MOVE_I4_TO_F:
+                       if (cfg->r4fp) {
+                               arm_fmov_rx_to_double (code, ins->dreg, ins->sreg1);
+                       } else {
+                               arm_fmov_rx_to_double (code, ins->dreg, ins->sreg1);
+                               arm_fcvt_sd (code, ins->dreg, ins->dreg);
+                       }
+                       break;
+               case OP_MOVE_F_TO_I8:
+                       arm_fmov_double_to_rx (code, ins->dreg, ins->sreg1);
+                       break;
+               case OP_MOVE_I8_TO_F:
+                       arm_fmov_rx_to_double (code, ins->dreg, ins->sreg1);
+                       break;
+               case OP_FCOMPARE:
+                       arm_fcmpd (code, sreg1, sreg2);
+                       break;
+               case OP_RCOMPARE:
+                       arm_fcmps (code, sreg1, sreg2);
+                       break;
+               case OP_FCONV_TO_I1:
+                       arm_fcvtzs_dx (code, dreg, sreg1);
+                       arm_sxtbx (code, dreg, dreg);
+                       break;
+               case OP_FCONV_TO_U1:
+                       arm_fcvtzu_dx (code, dreg, sreg1);
+                       arm_uxtbw (code, dreg, dreg);
+                       break;
+               case OP_FCONV_TO_I2:
+                       arm_fcvtzs_dx (code, dreg, sreg1);
+                       arm_sxthx (code, dreg, dreg);
+                       break;
+               case OP_FCONV_TO_U2:
+                       arm_fcvtzu_dx (code, dreg, sreg1);
+                       arm_uxthw (code, dreg, dreg);
+                       break;
+               case OP_FCONV_TO_I4:
+                       arm_fcvtzs_dx (code, dreg, sreg1);
+                       arm_sxtwx (code, dreg, dreg);
+                       break;
+               case OP_FCONV_TO_U4:
+                       arm_fcvtzu_dx (code, dreg, sreg1);
+                       break;
+               case OP_FCONV_TO_I8:
+                       arm_fcvtzs_dx (code, dreg, sreg1);
+                       break;
+               case OP_FCONV_TO_U8:
+                       arm_fcvtzu_dx (code, dreg, sreg1);
+                       break;
+               case OP_FCONV_TO_R4:
+                       if (cfg->r4fp) {
+                               arm_fcvt_ds (code, dreg, sreg1);
+                       } else {
+                               arm_fcvt_ds (code, FP_TEMP_REG, sreg1);
+                               arm_fcvt_sd (code, dreg, FP_TEMP_REG);
+                       }
+                       break;
+               case OP_ICONV_TO_R4:
+                       if (cfg->r4fp) {
+                               arm_scvtf_rw_to_s (code, dreg, sreg1);
+                       } else {
+                               arm_scvtf_rw_to_s (code, FP_TEMP_REG, sreg1);
+                               arm_fcvt_sd (code, dreg, FP_TEMP_REG);
+                       }
+                       break;
+               case OP_LCONV_TO_R4:
+                       if (cfg->r4fp) {
+                               arm_scvtf_rx_to_s (code, dreg, sreg1);
+                       } else {
+                               arm_scvtf_rx_to_s (code, FP_TEMP_REG, sreg1);
+                               arm_fcvt_sd (code, dreg, FP_TEMP_REG);
+                       }
+                       break;
+               case OP_ICONV_TO_R8:
+                       arm_scvtf_rw_to_d (code, dreg, sreg1);
+                       break;
+               case OP_LCONV_TO_R8:
+                       arm_scvtf_rx_to_d (code, dreg, sreg1);
+                       break;
+               case OP_ICONV_TO_R_UN:
+                       arm_ucvtf_rw_to_d (code, dreg, sreg1);
+                       break;
+               case OP_LCONV_TO_R_UN:
+                       arm_ucvtf_rx_to_d (code, dreg, sreg1);
+                       break;
+               case OP_FADD:
+                       arm_fadd_d (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_FSUB:
+                       arm_fsub_d (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_FMUL:
+                       arm_fmul_d (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_FDIV:
+                       arm_fdiv_d (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_FREM:
+                       /* Emulated */
+                       g_assert_not_reached ();
+                       break;
+               case OP_FNEG:
+                       arm_fneg_d (code, dreg, sreg1);
+                       break;
+               case OP_ARM_SETFREG_R4:
+                       arm_fcvt_ds (code, dreg, sreg1);
+                       break;
+               case OP_CKFINITE:
+                       /* Check for infinity */
+                       code = emit_imm64 (code, ARMREG_LR, 0x7fefffffffffffffLL);
+                       arm_fmov_rx_to_double (code, FP_TEMP_REG, ARMREG_LR);
+                       arm_fabs_d (code, FP_TEMP_REG2, sreg1);
+                       arm_fcmpd (code, FP_TEMP_REG2, FP_TEMP_REG);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_GT, "ArithmeticException");
+                       /* Check for nans */
+                       arm_fcmpd (code, FP_TEMP_REG2, FP_TEMP_REG2);
+                       code = emit_cond_exc (cfg, code, OP_COND_EXC_OV, "ArithmeticException");
+                       arm_fmovd (code, dreg, sreg1);
+                       break;
+
+                       /* R4 */
+               case OP_RADD:
+                       arm_fadd_s (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_RSUB:
+                       arm_fsub_s (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_RMUL:
+                       arm_fmul_s (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_RDIV:
+                       arm_fdiv_s (code, dreg, sreg1, sreg2);
+                       break;
+               case OP_RNEG:
+                       arm_fneg_s (code, dreg, sreg1);
+                       break;
+               case OP_RCONV_TO_I1:
+                       arm_fcvtzs_sx (code, dreg, sreg1);
+                       arm_sxtbx (code, dreg, dreg);
+                       break;
+               case OP_RCONV_TO_U1:
+                       arm_fcvtzu_sx (code, dreg, sreg1);
+                       arm_uxtbw (code, dreg, dreg);
+                       break;
+               case OP_RCONV_TO_I2:
+                       arm_fcvtzs_sx (code, dreg, sreg1);
+                       arm_sxthx (code, dreg, dreg);
+                       break;
+               case OP_RCONV_TO_U2:
+                       arm_fcvtzu_sx (code, dreg, sreg1);
+                       arm_uxthw (code, dreg, dreg);
+                       break;
+               case OP_RCONV_TO_I4:
+                       arm_fcvtzs_sx (code, dreg, sreg1);
+                       arm_sxtwx (code, dreg, dreg);
+                       break;
+               case OP_RCONV_TO_U4:
+                       arm_fcvtzu_sx (code, dreg, sreg1);
+                       break;
+               case OP_RCONV_TO_I8:
+                       arm_fcvtzs_sx (code, dreg, sreg1);
+                       break;
+               case OP_RCONV_TO_U8:
+                       arm_fcvtzu_sx (code, dreg, sreg1);
+                       break;
+               case OP_RCONV_TO_R8:
+                       arm_fcvt_sd (code, dreg, sreg1);
+                       break;
+               case OP_RCONV_TO_R4:
+                       if (dreg != sreg1)
+                               arm_fmovs (code, dreg, sreg1);
+                       break;
+               case OP_RCEQ:
+               case OP_RCLT:
+               case OP_RCLT_UN:
+               case OP_RCGT:
+               case OP_RCGT_UN:
+               case OP_RCNEQ:
+               case OP_RCLE:
+               case OP_RCGE: {
+                       int cond;
+
+                       cond = opcode_to_armcond (ins->opcode);
+                       arm_fcmps (code, sreg1, sreg2);
+                       arm_cset (code, cond, dreg);
+                       break;
+               }
+
+                       /* CALLS */
+               case OP_VOIDCALL:
+               case OP_CALL:
+               case OP_LCALL:
+               case OP_FCALL:
+               case OP_RCALL:
+               case OP_VCALL2:
+                       call = (MonoCallInst*)ins;
+                       if (ins->flags & MONO_INST_HAS_METHOD)
+                               code = emit_call (cfg, code, MONO_PATCH_INFO_METHOD, call->method);
+                       else
+                               code = emit_call (cfg, code, MONO_PATCH_INFO_ABS, call->fptr);
+                       code = emit_move_return_value (cfg, code, ins);
+                       break;
+               case OP_VOIDCALL_REG:
+               case OP_CALL_REG:
+               case OP_LCALL_REG:
+               case OP_FCALL_REG:
+               case OP_RCALL_REG:
+               case OP_VCALL2_REG:
+                       arm_blrx (code, sreg1);
+                       code = emit_move_return_value (cfg, code, ins);
+                       break;
+               case OP_VOIDCALL_MEMBASE:
+               case OP_CALL_MEMBASE:
+               case OP_LCALL_MEMBASE:
+               case OP_FCALL_MEMBASE:
+               case OP_RCALL_MEMBASE:
+               case OP_VCALL2_MEMBASE:
+                       code = emit_ldrx (code, ARMREG_IP0, ins->inst_basereg, ins->inst_offset);
+                       arm_blrx (code, ARMREG_IP0);
+                       code = emit_move_return_value (cfg, code, ins);
+                       break;
+               case OP_TAILCALL: {
+                       MonoCallInst *call = (MonoCallInst*)ins;
+
+                       g_assert (!cfg->method->save_lmf);
+
+                       // FIXME: Copy stack arguments
+
+                       /* Restore registers */
+                       code = emit_load_regset (code, MONO_ARCH_CALLEE_SAVED_REGS & cfg->used_int_regs, ARMREG_FP, cfg->arch.saved_gregs_offset);
+
+                       /* Destroy frame */
+                       code = mono_arm_emit_destroy_frame (code, cfg->stack_offset, ((1 << ARMREG_IP0) | (1 << ARMREG_IP1)));
+
+                       if (cfg->compile_aot) {
+                               /* This is not a PLT patch */
+                               code = emit_aotconst (cfg, code, ARMREG_IP0, MONO_PATCH_INFO_METHOD_JUMP, call->method);
+                               arm_brx (code, ARMREG_IP0);
+                       } else {
+                               mono_add_patch_info_rel (cfg, code - cfg->native_code, MONO_PATCH_INFO_METHOD_JUMP, call->method, MONO_R_ARM64_B);
+                               arm_b (code, code);
+                       }
+                       ins->flags |= MONO_INST_GC_CALLSITE;
+                       ins->backend.pc_offset = code - cfg->native_code;
+                       break;
+               }
+               case OP_ARGLIST:
+                       g_assert (cfg->arch.cinfo);
+                       code = emit_addx_imm (code, ARMREG_IP0, cfg->arch.args_reg, ((CallInfo*)cfg->arch.cinfo)->sig_cookie.offset);
+                       arm_strx (code, ARMREG_IP0, sreg1, 0);
+                       break;
+               case OP_DYN_CALL: {
+                       MonoInst *var = cfg->dyn_call_var;
+                       guint8 *labels [16];
+                       int i;
+
+                       /*
+                        * sreg1 points to a DynCallArgs structure initialized by mono_arch_start_dyn_call ().
+                        * sreg2 is the function to call.
+                        */
+
+                       g_assert (var->opcode == OP_REGOFFSET);
+
+                       arm_movx (code, ARMREG_LR, sreg1);
+                       arm_movx (code, ARMREG_IP1, sreg2);
+
+                       /* Save args buffer */
+                       code = emit_strx (code, ARMREG_LR, var->inst_basereg, var->inst_offset);
+
+                       /* Set fp argument regs */
+                       code = emit_ldrw (code, ARMREG_R0, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, n_fpargs));
+                       arm_cmpw (code, ARMREG_R0, ARMREG_RZR);
+                       labels [0] = code;
+                       arm_bcc (code, ARMCOND_EQ, 0);
+                       for (i = 0; i < 8; ++i)
+                               code = emit_ldrfpx (code, ARMREG_D0 + i, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, fpregs) + (i * 8));
+                       arm_patch_rel (labels [0], code, MONO_R_ARM64_BCC);
+
+                       /* Set stack args */
+                       for (i = 0; i < DYN_CALL_STACK_ARGS; ++i) {
+                               code = emit_ldrx (code, ARMREG_R0, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, regs) + ((PARAM_REGS + 1 + i) * sizeof (mgreg_t)));
+                               code = emit_strx (code, ARMREG_R0, ARMREG_SP, i * sizeof (mgreg_t));
+                       }
+
+                       /* Set argument registers + r8 */
+                       code = mono_arm_emit_load_regarray (code, 0x1ff, ARMREG_LR, 0);
+
+                       /* Make the call */
+                       arm_blrx (code, ARMREG_IP1);
+
+                       /* Save result */
+                       code = emit_ldrx (code, ARMREG_LR, var->inst_basereg, var->inst_offset);
+                       arm_strx (code, ARMREG_R0, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, res));
+                       arm_strx (code, ARMREG_R1, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, res2));
+                       /* Save fp result */
+                       code = emit_ldrw (code, ARMREG_R0, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, n_fpret));
+                       arm_cmpw (code, ARMREG_R0, ARMREG_RZR);
+                       labels [1] = code;
+                       arm_bcc (code, ARMCOND_EQ, 0);
+                       for (i = 0; i < 8; ++i)
+                               code = emit_strfpx (code, ARMREG_D0 + i, ARMREG_LR, MONO_STRUCT_OFFSET (DynCallArgs, fpregs) + (i * 8));
+                       arm_patch_rel (labels [1], code, MONO_R_ARM64_BCC);
+                       break;
+               }
+
+               case OP_GENERIC_CLASS_INIT: {
+                       static int byte_offset = -1;
+                       static guint8 bitmask;
+                       guint8 *jump;
+
+                       if (byte_offset < 0)
+                               mono_marshal_find_bitfield_offset (MonoVTable, initialized, &byte_offset, &bitmask);
+
+                       /* Load vtable->initialized */
+                       arm_ldrsbx (code, ARMREG_IP0, sreg1, byte_offset);
+                       // FIXME: No andx_imm yet */
+                       code = mono_arm_emit_imm64 (code, ARMREG_IP1, bitmask);
+                       arm_andx (code, ARMREG_IP0, ARMREG_IP0, ARMREG_IP1);
+                       jump = code;
+                       arm_cbnzx (code, ARMREG_IP0, 0);
+
+                       /* Slowpath */
+                       g_assert (sreg1 == ARMREG_R0);
+                       code = emit_call (cfg, code, MONO_PATCH_INFO_INTERNAL_METHOD,
+                                                         (gpointer)"mono_generic_class_init");
+
+                       mono_arm_patch (jump, code, MONO_R_ARM64_CBZ);
+                       break;
+               }
+
+               case OP_CHECK_THIS:
+                       arm_ldrx (code, ARMREG_LR, sreg1, 0);
+                       break;
+               case OP_NOT_NULL:
+               case OP_NOT_REACHED:
+               case OP_DUMMY_USE:
+                       break;
+               case OP_IL_SEQ_POINT:
+                       mono_add_seq_point (cfg, bb, ins, code - cfg->native_code);
+                       break;
+
+                       /* EH */
+               case OP_COND_EXC_C:
+               case OP_COND_EXC_IC:
+               case OP_COND_EXC_OV:
+               case OP_COND_EXC_IOV:
+               case OP_COND_EXC_NC:
+               case OP_COND_EXC_INC:
+               case OP_COND_EXC_NO:
+               case OP_COND_EXC_INO:
+               case OP_COND_EXC_EQ:
+               case OP_COND_EXC_IEQ:
+               case OP_COND_EXC_NE_UN:
+               case OP_COND_EXC_INE_UN:
+               case OP_COND_EXC_ILT:
+               case OP_COND_EXC_LT:
+               case OP_COND_EXC_ILT_UN:
+               case OP_COND_EXC_LT_UN:
+               case OP_COND_EXC_IGT:
+               case OP_COND_EXC_GT:
+               case OP_COND_EXC_IGT_UN:
+               case OP_COND_EXC_GT_UN:
+               case OP_COND_EXC_IGE:
+               case OP_COND_EXC_GE:
+               case OP_COND_EXC_IGE_UN:
+               case OP_COND_EXC_GE_UN:
+               case OP_COND_EXC_ILE:
+               case OP_COND_EXC_LE:
+               case OP_COND_EXC_ILE_UN:
+               case OP_COND_EXC_LE_UN:
+                       code = emit_cond_exc (cfg, code, ins->opcode, ins->inst_p1);
+                       break;
+               case OP_THROW:
+                       if (sreg1 != ARMREG_R0)
+                               arm_movx (code, ARMREG_R0, sreg1);
+                       code = emit_call (cfg, code, MONO_PATCH_INFO_INTERNAL_METHOD, 
+                                                         (gpointer)"mono_arch_throw_exception");
+                       break;
+               case OP_RETHROW:
+                       if (sreg1 != ARMREG_R0)
+                               arm_movx (code, ARMREG_R0, sreg1);
+                       code = emit_call (cfg, code, MONO_PATCH_INFO_INTERNAL_METHOD, 
+                                                         (gpointer)"mono_arch_rethrow_exception");
+                       break;
+               case OP_CALL_HANDLER:
+                       mono_add_patch_info_rel (cfg, offset, MONO_PATCH_INFO_BB, ins->inst_target_bb, MONO_R_ARM64_BL);
+                       arm_bl (code, 0);
+                       cfg->thunk_area += THUNK_SIZE;
+                       break;
+               case OP_START_HANDLER: {
+                       MonoInst *spvar = mono_find_spvar_for_region (cfg, bb->region);
+
+                       /* Save caller address */
+                       code = emit_strx (code, ARMREG_LR, spvar->inst_basereg, spvar->inst_offset);
+
+                       /*
+                        * Reserve a param area, see test_0_finally_param_area ().
+                        * This is needed because the param area is not set up when
+                        * we are called from EH code.
+                        */
+                       if (cfg->param_area)
+                               code = emit_subx_sp_imm (code, cfg->param_area);
+                       break;
+               }
+               case OP_ENDFINALLY:
+               case OP_ENDFILTER: {
+                       MonoInst *spvar = mono_find_spvar_for_region (cfg, bb->region);
+
+                       if (cfg->param_area)
+                               code = emit_addx_sp_imm (code, cfg->param_area);
+
+                       if (ins->opcode == OP_ENDFILTER && sreg1 != ARMREG_R0)
+                               arm_movx (code, ARMREG_R0, sreg1);
+
+                       /* Return to either after the branch in OP_CALL_HANDLER, or to the EH code */
+                       code = emit_ldrx (code, ARMREG_LR, spvar->inst_basereg, spvar->inst_offset);
+                       arm_brx (code, ARMREG_LR);
+                       break;
+               }
+               case OP_GET_EX_OBJ:
+                       if (ins->dreg != ARMREG_R0)
+                               arm_movx (code, ins->dreg, ARMREG_R0);
+                       break;
+               case OP_GC_SAFE_POINT: {
+#if defined (USE_COOP_GC)
+                       guint8 *buf [1];
+
+                       arm_ldrx (code, ARMREG_IP1, ins->sreg1, 0);
+                       /* Call it if it is non-null */
+                       buf [0] = code;
+                       arm_cbzx (code, ARMREG_IP1, 0);
+                       code = emit_call (cfg, code, MONO_PATCH_INFO_INTERNAL_METHOD, "mono_threads_state_poll");
+                       mono_arm_patch (buf [0], code, MONO_R_ARM64_CBZ);
+#endif
+                       break;
+               }
+
+               default:
+                       g_warning ("unknown opcode %s in %s()\n", mono_inst_name (ins->opcode), __FUNCTION__);
+                       g_assert_not_reached ();
+               }
+
+               if ((cfg->opt & MONO_OPT_BRANCH) && ((code - cfg->native_code - offset) > max_len)) {
+                       g_warning ("wrong maximal instruction length of instruction %s (expected %d, got %d)",
+                                  mono_inst_name (ins->opcode), max_len, code - cfg->native_code - offset);
+                       g_assert_not_reached ();
+               }
+       }
+
+       /*
+        * If the compiled code size is larger than the bcc displacement (19 bits signed),
+        * insert branch islands between/inside basic blocks.
+        */
+       if (cfg->arch.cond_branch_islands)
+               code = emit_branch_island (cfg, code, start_offset);
+
+       cfg->code_len = code - cfg->native_code;
+}
+
+static guint8*
+emit_move_args (MonoCompile *cfg, guint8 *code)
+{
+       MonoInst *ins;
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
+       int i, part;
+
+       cinfo = cfg->arch.cinfo;
+       g_assert (cinfo);
+       for (i = 0; i < cinfo->nargs; ++i) {
+               ainfo = cinfo->args + i;
+               ins = cfg->args [i];
+
+               if (ins->opcode == OP_REGVAR) {
+                       switch (ainfo->storage) {
+                       case ArgInIReg:
+                               arm_movx (code, ins->dreg, ainfo->reg);
+                               break;
+                       case ArgOnStack:
+                               switch (ainfo->slot_size) {
+                               case 1:
+                                       if (ainfo->sign)
+                                               code = emit_ldrsbx (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       else
+                                               code = emit_ldrb (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       break;
+                               case 2:
+                                       if (ainfo->sign)
+                                               code = emit_ldrshx (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       else
+                                               code = emit_ldrh (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       break;
+                               case 4:
+                                       if (ainfo->sign)
+                                               code = emit_ldrswx (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       else
+                                               code = emit_ldrw (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       break;
+                               default:
+                                       code = emit_ldrx (code, ins->dreg, cfg->arch.args_reg, ainfo->offset);
+                                       break;
+                               }
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                               break;
+                       }
+               } else {
+                       if (ainfo->storage != ArgVtypeByRef && ainfo->storage != ArgVtypeByRefOnStack)
+                               g_assert (ins->opcode == OP_REGOFFSET);
+
+                       switch (ainfo->storage) {
+                       case ArgInIReg:
+                               /* Stack slots for arguments have size 8 */
+                               code = emit_strx (code, ainfo->reg, ins->inst_basereg, ins->inst_offset);
+                               break;
+                       case ArgInFReg:
+                               code = emit_strfpx (code, ainfo->reg, ins->inst_basereg, ins->inst_offset);
+                               break;
+                       case ArgInFRegR4:
+                               code = emit_strfpw (code, ainfo->reg, ins->inst_basereg, ins->inst_offset);
+                               break;
+                       case ArgOnStack:
+                       case ArgOnStackR4:
+                       case ArgOnStackR8:
+                       case ArgVtypeByRefOnStack:
+                       case ArgVtypeOnStack:
+                               break;
+                       case ArgVtypeByRef: {
+                               MonoInst *addr_arg = ins->inst_left;
+
+                               if (ainfo->gsharedvt) {
+                                       g_assert (ins->opcode == OP_GSHAREDVT_ARG_REGOFFSET);
+                                       arm_strx (code, ainfo->reg, ins->inst_basereg, ins->inst_offset);
+                               } else {
+                                       g_assert (ins->opcode == OP_VTARG_ADDR);
+                                       g_assert (addr_arg->opcode == OP_REGOFFSET);
+                                       arm_strx (code, ainfo->reg, addr_arg->inst_basereg, addr_arg->inst_offset);
+                               }
+                               break;
+                       }
+                       case ArgVtypeInIRegs:
+                               for (part = 0; part < ainfo->nregs; part ++) {
+                                       code = emit_strx (code, ainfo->reg + part, ins->inst_basereg, ins->inst_offset + (part * 8));
+                               }
+                               break;
+                       case ArgHFA:
+                               for (part = 0; part < ainfo->nregs; part ++) {
+                                       if (ainfo->esize == 4)
+                                               code = emit_strfpw (code, ainfo->reg + part, ins->inst_basereg, ins->inst_offset + ainfo->foffsets [part]);
+                                       else
+                                               code = emit_strfpx (code, ainfo->reg + part, ins->inst_basereg, ins->inst_offset + ainfo->foffsets [part]);
+                               }
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                               break;
+                       }
+               }
+       }
+
+       return code;
+}
+
+/*
+ * emit_store_regarray:
+ *
+ *   Emit code to store the registers in REGS into the appropriate elements of
+ * the register array at BASEREG+OFFSET.
+ */
+static __attribute__((warn_unused_result)) guint8*
+emit_store_regarray (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       int i;
+
+       for (i = 0; i < 32; ++i) {
+               if (regs & (1 << i)) {
+                       if (i + 1 < 32 && (regs & (1 << (i + 1))) && (i + 1 != ARMREG_SP)) {
+                               arm_stpx (code, i, i + 1, basereg, offset + (i * 8));
+                               i++;
+                       } else if (i == ARMREG_SP) {
+                               arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+                               arm_strx (code, ARMREG_IP1, basereg, offset + (i * 8));
+                       } else {
+                               arm_strx (code, i, basereg, offset + (i * 8));
+                       }
+               }
+       }
+       return code;
+}
+
+/*
+ * emit_load_regarray:
+ *
+ *   Emit code to load the registers in REGS from the appropriate elements of
+ * the register array at BASEREG+OFFSET.
+ */
+static __attribute__((warn_unused_result)) guint8*
+emit_load_regarray (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       int i;
+
+       for (i = 0; i < 32; ++i) {
+               if (regs & (1 << i)) {
+                       if ((regs & (1 << (i + 1))) && (i + 1 != ARMREG_SP)) {
+                               if (offset + (i * 8) < 500)
+                                       arm_ldpx (code, i, i + 1, basereg, offset + (i * 8));
+                               else {
+                                       code = emit_ldrx (code, i, basereg, offset + (i * 8));
+                                       code = emit_ldrx (code, i + 1, basereg, offset + ((i + 1) * 8));
+                               }
+                               i++;
+                       } else if (i == ARMREG_SP) {
+                               g_assert_not_reached ();
+                       } else {
+                               code = emit_ldrx (code, i, basereg, offset + (i * 8));
+                       }
+               }
+       }
+       return code;
+}
+
+/*
+ * emit_store_regset:
+ *
+ *   Emit code to store the registers in REGS into consecutive memory locations starting
+ * at BASEREG+OFFSET.
+ */
+static __attribute__((warn_unused_result)) guint8*
+emit_store_regset (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       int i, pos;
+
+       pos = 0;
+       for (i = 0; i < 32; ++i) {
+               if (regs & (1 << i)) {
+                       if ((regs & (1 << (i + 1))) && (i + 1 != ARMREG_SP)) {
+                               arm_stpx (code, i, i + 1, basereg, offset + (pos * 8));
+                               i++;
+                               pos++;
+                       } else if (i == ARMREG_SP) {
+                               arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+                               arm_strx (code, ARMREG_IP1, basereg, offset + (pos * 8));
+                       } else {
+                               arm_strx (code, i, basereg, offset + (pos * 8));
+                       }
+                       pos++;
+               }
+       }
+       return code;
+}
+
+/*
+ * emit_load_regset:
+ *
+ *   Emit code to load the registers in REGS from consecutive memory locations starting
+ * at BASEREG+OFFSET.
+ */
+static __attribute__((warn_unused_result)) guint8*
+emit_load_regset (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       int i, pos;
+
+       pos = 0;
+       for (i = 0; i < 32; ++i) {
+               if (regs & (1 << i)) {
+                       if ((regs & (1 << (i + 1))) && (i + 1 != ARMREG_SP)) {
+                               arm_ldpx (code, i, i + 1, basereg, offset + (pos * 8));
+                               i++;
+                               pos++;
+                       } else if (i == ARMREG_SP) {
+                               g_assert_not_reached ();
+                       } else {
+                               arm_ldrx (code, i, basereg, offset + (pos * 8));
+                       }
+                       pos++;
+               }
+       }
+       return code;
+}
+
+__attribute__((warn_unused_result)) guint8*
+mono_arm_emit_load_regarray (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       return emit_load_regarray (code, regs, basereg, offset);
+}
+
+__attribute__((warn_unused_result)) guint8*
+mono_arm_emit_store_regarray (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       return emit_store_regarray (code, regs, basereg, offset);
+}
+
+__attribute__((warn_unused_result)) guint8*
+mono_arm_emit_store_regset (guint8 *code, guint64 regs, int basereg, int offset)
+{
+       return emit_store_regset (code, regs, basereg, offset);
+}
+
+/* Same as emit_store_regset, but emit unwind info too */
+/* CFA_OFFSET is the offset between the CFA and basereg */
+static __attribute__((warn_unused_result)) guint8*
+emit_store_regset_cfa (MonoCompile *cfg, guint8 *code, guint64 regs, int basereg, int offset, int cfa_offset, guint64 no_cfa_regset)
+{
+       int i, j, pos, nregs;
+       guint32 cfa_regset = regs & ~no_cfa_regset;
+
+       pos = 0;
+       for (i = 0; i < 32; ++i) {
+               nregs = 1;
+               if (regs & (1 << i)) {
+                       if ((regs & (1 << (i + 1))) && (i + 1 != ARMREG_SP)) {
+                               if (offset < 256) {
+                                       arm_stpx (code, i, i + 1, basereg, offset + (pos * 8));
+                               } else {
+                                       code = emit_strx (code, i, basereg, offset + (pos * 8));
+                                       code = emit_strx (code, i + 1, basereg, offset + (pos * 8) + 8);
+                               }
+                               nregs = 2;
+                       } else if (i == ARMREG_SP) {
+                               arm_movspx (code, ARMREG_IP1, ARMREG_SP);
+                               code = emit_strx (code, ARMREG_IP1, basereg, offset + (pos * 8));
+                       } else {
+                               code = emit_strx (code, i, basereg, offset + (pos * 8));
+                       }
+
+                       for (j = 0; j < nregs; ++j) {
+                               if (cfa_regset & (1 << (i + j)))
+                                       mono_emit_unwind_op_offset (cfg, code, i + j, (- cfa_offset) + offset + ((pos + j) * 8));
+                       }
+
+                       i += nregs - 1;
+                       pos += nregs;
+               }
+       }
+       return code;
+}
+
+/*
+ * emit_setup_lmf:
+ *
+ *   Emit code to initialize an LMF structure at LMF_OFFSET.
+ * Clobbers ip0/ip1.
+ */
+static guint8*
+emit_setup_lmf (MonoCompile *cfg, guint8 *code, gint32 lmf_offset, int cfa_offset)
+{
+       /*
+        * The LMF should contain all the state required to be able to reconstruct the machine state
+        * at the current point of execution. Since the LMF is only read during EH, only callee
+        * saved etc. registers need to be saved.
+        * FIXME: Save callee saved fp regs, JITted code doesn't use them, but native code does, and they
+        * need to be restored during EH.
+        */
+
+       /* pc */
+       arm_adrx (code, ARMREG_LR, code);
+       code = emit_strx (code, ARMREG_LR, ARMREG_FP, lmf_offset + MONO_STRUCT_OFFSET (MonoLMF, pc));
+       /* gregs + fp + sp */
+       /* Don't emit unwind info for sp/fp, they are already handled in the prolog */
+       code = emit_store_regset_cfa (cfg, code, MONO_ARCH_LMF_REGS, ARMREG_FP, lmf_offset + MONO_STRUCT_OFFSET (MonoLMF, gregs), cfa_offset, (1 << ARMREG_FP) | (1 << ARMREG_SP));
+
+       return code;
+}
+
+guint8 *
+mono_arch_emit_prolog (MonoCompile *cfg)
+{
+       MonoMethod *method = cfg->method;
+       MonoMethodSignature *sig;
+       MonoBasicBlock *bb;
+       guint8 *code;
+       int cfa_offset, max_offset;
+
+       sig = mono_method_signature (method);
+       cfg->code_size = 256 + sig->param_count * 64;
+       code = cfg->native_code = g_malloc (cfg->code_size);
+
+       /* This can be unaligned */
+       cfg->stack_offset = ALIGN_TO (cfg->stack_offset, MONO_ARCH_FRAME_ALIGNMENT);
+
+       /*
+        * - Setup frame
+        */
+       cfa_offset = 0;
+       mono_emit_unwind_op_def_cfa (cfg, code, ARMREG_SP, 0);
+
+       /* Setup frame */
+       if (arm_is_ldpx_imm (-cfg->stack_offset)) {
+               arm_stpx_pre (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, -cfg->stack_offset);
+       } else {
+               /* sp -= cfg->stack_offset */
+               /* This clobbers ip0/ip1 */
+               code = emit_subx_sp_imm (code, cfg->stack_offset);
+               arm_stpx (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, 0);
+       }
+       cfa_offset += cfg->stack_offset;
+       mono_emit_unwind_op_def_cfa_offset (cfg, code, cfa_offset);
+       mono_emit_unwind_op_offset (cfg, code, ARMREG_FP, (- cfa_offset) + 0);
+       mono_emit_unwind_op_offset (cfg, code, ARMREG_LR, (- cfa_offset) + 8);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+       mono_emit_unwind_op_def_cfa_reg (cfg, code, ARMREG_FP);
+       if (cfg->param_area) {
+               /* The param area is below the frame pointer */
+               code = emit_subx_sp_imm (code, cfg->param_area);
+       }
+
+       if (cfg->method->save_lmf) {
+               code = emit_setup_lmf (cfg, code, cfg->lmf_var->inst_offset, cfa_offset);
+       } else {
+               /* Save gregs */
+               code = emit_store_regset_cfa (cfg, code, MONO_ARCH_CALLEE_SAVED_REGS & cfg->used_int_regs, ARMREG_FP, cfg->arch.saved_gregs_offset, cfa_offset, 0);
+       }
+
+       /* Setup args reg */
+       if (cfg->arch.args_reg) {
+               /* The register was already saved above */
+               code = emit_addx_imm (code, cfg->arch.args_reg, ARMREG_FP, cfg->stack_offset);
+       }
+
+       /* Save return area addr received in R8 */
+       if (cfg->vret_addr) {
+               MonoInst *ins = cfg->vret_addr;
+
+               g_assert (ins->opcode == OP_REGOFFSET);
+               code = emit_strx (code, ARMREG_R8, ins->inst_basereg, ins->inst_offset);
+       }
+
+       /* Save mrgctx received in MONO_ARCH_RGCTX_REG */
+       if (cfg->rgctx_var) {
+               MonoInst *ins = cfg->rgctx_var;
+
+               g_assert (ins->opcode == OP_REGOFFSET);
+
+               code = emit_strx (code, MONO_ARCH_RGCTX_REG, ins->inst_basereg, ins->inst_offset); 
+       }
+               
+       /*
+        * Move arguments to their registers/stack locations.
+        */
+       code = emit_move_args (cfg, code);
+
+       /* Initialize seq_point_info_var */
+       if (cfg->arch.seq_point_info_var) {
+               MonoInst *ins = cfg->arch.seq_point_info_var;
+
+               /* Initialize the variable from a GOT slot */
+               code = emit_aotconst (cfg, code, ARMREG_IP0, MONO_PATCH_INFO_SEQ_POINT_INFO, cfg->method);
+               g_assert (ins->opcode == OP_REGOFFSET);
+               code = emit_strx (code, ARMREG_IP0, ins->inst_basereg, ins->inst_offset);
+
+               /* Initialize ss_tramp_var */
+               ins = cfg->arch.ss_tramp_var;
+               g_assert (ins->opcode == OP_REGOFFSET);
+
+               code = emit_ldrx (code, ARMREG_IP1, ARMREG_IP0, MONO_STRUCT_OFFSET (SeqPointInfo, ss_tramp_addr));
+               code = emit_strx (code, ARMREG_IP1, ins->inst_basereg, ins->inst_offset);
+       } else {
+               MonoInst *ins;
+
+               if (cfg->arch.ss_tramp_var) {
+                       /* Initialize ss_tramp_var */
+                       ins = cfg->arch.ss_tramp_var;
+                       g_assert (ins->opcode == OP_REGOFFSET);
+
+                       code = emit_imm64 (code, ARMREG_IP0, (guint64)&ss_trampoline);
+                       code = emit_strx (code, ARMREG_IP0, ins->inst_basereg, ins->inst_offset);
+               }
+
+               if (cfg->arch.bp_tramp_var) {
+                       /* Initialize bp_tramp_var */
+                       ins = cfg->arch.bp_tramp_var;
+                       g_assert (ins->opcode == OP_REGOFFSET);
+
+                       code = emit_imm64 (code, ARMREG_IP0, (guint64)bp_trampoline);
+                       code = emit_strx (code, ARMREG_IP0, ins->inst_basereg, ins->inst_offset);
+               }
+       }
+
+       max_offset = 0;
+       if (cfg->opt & MONO_OPT_BRANCH) {
+               for (bb = cfg->bb_entry; bb; bb = bb->next_bb) {
+                       MonoInst *ins;
+                       bb->max_offset = max_offset;
+
+                       MONO_BB_FOR_EACH_INS (bb, ins) {
+                               max_offset += ((guint8 *)ins_get_spec (ins->opcode))[MONO_INST_LEN];
+                       }
+               }
+       }
+       if (max_offset > 0x3ffff * 4)
+               cfg->arch.cond_branch_islands = TRUE;
+
+       return code;
+}
+
+static guint8*
+realloc_code (MonoCompile *cfg, int size)
+{
+       while (cfg->code_len + size > (cfg->code_size - 16)) {
+               cfg->code_size *= 2;
+               cfg->native_code = g_realloc (cfg->native_code, cfg->code_size);
+               cfg->stat_code_reallocs++;
+       }
+       return cfg->native_code + cfg->code_len;
+}
+
+void
+mono_arch_emit_epilog (MonoCompile *cfg)
+{
+       CallInfo *cinfo;
+       int max_epilog_size;
+       guint8 *code;
+       int i;
+
+       max_epilog_size = 16 + 20*4;
+       code = realloc_code (cfg, max_epilog_size);
+
+       if (cfg->method->save_lmf) {
+               code = mono_arm_emit_load_regarray (code, MONO_ARCH_CALLEE_SAVED_REGS & cfg->used_int_regs, ARMREG_FP, cfg->lmf_var->inst_offset + MONO_STRUCT_OFFSET (MonoLMF, gregs) - (MONO_ARCH_FIRST_LMF_REG * 8));
+       } else {
+               /* Restore gregs */
+               code = emit_load_regset (code, MONO_ARCH_CALLEE_SAVED_REGS & cfg->used_int_regs, ARMREG_FP, cfg->arch.saved_gregs_offset);
+       }
+
+       /* Load returned vtypes into registers if needed */
+       cinfo = cfg->arch.cinfo;
+       switch (cinfo->ret.storage) {
+       case ArgVtypeInIRegs: {
+               MonoInst *ins = cfg->ret;
+
+               for (i = 0; i < cinfo->ret.nregs; ++i)
+                       code = emit_ldrx (code, cinfo->ret.reg + i, ins->inst_basereg, ins->inst_offset + (i * 8));
+               break;
+       }
+       case ArgHFA: {
+               MonoInst *ins = cfg->ret;
+
+               for (i = 0; i < cinfo->ret.nregs; ++i) {
+                       if (cinfo->ret.esize == 4)
+                               code = emit_ldrfpw (code, cinfo->ret.reg + i, ins->inst_basereg, ins->inst_offset + cinfo->ret.foffsets [i]);
+                       else
+                               code = emit_ldrfpx (code, cinfo->ret.reg + i, ins->inst_basereg, ins->inst_offset + cinfo->ret.foffsets [i]);
+               }
+               break;
+       }
+       default:
+               break;
+       }
+
+       /* Destroy frame */
+       code = mono_arm_emit_destroy_frame (code, cfg->stack_offset, ((1 << ARMREG_IP0) | (1 << ARMREG_IP1)));
+
+       arm_retx (code, ARMREG_LR);
+
+       g_assert (code - (cfg->native_code + cfg->code_len) < max_epilog_size);
+
+       cfg->code_len = code - cfg->native_code;
+}
+
+void
+mono_arch_emit_exceptions (MonoCompile *cfg)
+{
+       MonoJumpInfo *ji;
+       MonoClass *exc_class;
+       guint8 *code, *ip;
+       guint8* exc_throw_pos [MONO_EXC_INTRINS_NUM];
+       guint8 exc_throw_found [MONO_EXC_INTRINS_NUM];
+       int i, id, size = 0;
+
+       for (i = 0; i < MONO_EXC_INTRINS_NUM; i++) {
+               exc_throw_pos [i] = NULL;
+               exc_throw_found [i] = 0;
+       }
+
+       for (ji = cfg->patch_info; ji; ji = ji->next) {
+               if (ji->type == MONO_PATCH_INFO_EXC) {
+                       i = mini_exception_id_by_name (ji->data.target);
+                       if (!exc_throw_found [i]) {
+                               size += 32;
+                               exc_throw_found [i] = TRUE;
+                       }
+               }
+       }
+
+       code = realloc_code (cfg, size);
+
+       /* Emit code to raise corlib exceptions */
+       for (ji = cfg->patch_info; ji; ji = ji->next) {
+               if (ji->type != MONO_PATCH_INFO_EXC)
+                       continue;
+
+               ip = cfg->native_code + ji->ip.i;
+
+               id = mini_exception_id_by_name (ji->data.target);
+
+               if (exc_throw_pos [id]) {
+                       /* ip points to the bcc () in OP_COND_EXC_... */
+                       arm_patch_rel (ip, exc_throw_pos [id], ji->relocation);
+                       ji->type = MONO_PATCH_INFO_NONE;
+                       continue;
+               }
+
+               exc_throw_pos [id] = code;
+               arm_patch_rel (ip, code, ji->relocation);
+
+               /* We are being branched to from the code generated by emit_cond_exc (), the pc is in ip1 */
+
+               /* r0 = type token */
+               exc_class = mono_class_load_from_name (mono_defaults.corlib, "System", ji->data.name);
+               code = emit_imm (code, ARMREG_R0, exc_class->type_token - MONO_TOKEN_TYPE_DEF);
+               /* r1 = throw ip */
+               arm_movx (code, ARMREG_R1, ARMREG_IP1);
+               /* Branch to the corlib exception throwing trampoline */
+               ji->ip.i = code - cfg->native_code;
+               ji->type = MONO_PATCH_INFO_INTERNAL_METHOD;
+               ji->data.name = "mono_arch_throw_corlib_exception";
+               ji->relocation = MONO_R_ARM64_BL;
+               arm_bl (code, 0);
+               cfg->thunk_area += THUNK_SIZE;
+       }
+
+       cfg->code_len = code - cfg->native_code;
+
+       g_assert (cfg->code_len < cfg->code_size);
+}
+
+MonoInst*
+mono_arch_emit_inst_for_method (MonoCompile *cfg, MonoMethod *cmethod, MonoMethodSignature *fsig, MonoInst **args)
+{
+       return NULL;
+}
+
+gboolean
+mono_arch_print_tree (MonoInst *tree, int arity)
+{
+       return FALSE;
+}
+
+guint32
+mono_arch_get_patch_offset (guint8 *code)
+{
+       return 0;
+}
+
+gpointer
+mono_arch_build_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count,
+                                                  gpointer fail_tramp)
+{
+       int i, buf_len, imt_reg;
+       guint8 *buf, *code;
+
+#if DEBUG_IMT
+       printf ("building IMT thunk for class %s %s entries %d code size %d code at %p end %p vtable %p\n", vtable->klass->name_space, vtable->klass->name, count, size, start, ((guint8*)start) + size, vtable);
+       for (i = 0; i < count; ++i) {
+               MonoIMTCheckItem *item = imt_entries [i];
+               printf ("method %d (%p) %s vtable slot %p is_equals %d chunk size %d\n", i, item->key, item->key->name, &vtable->vtable [item->value.vtable_slot], item->is_equals, item->chunk_size);
+       }
+#endif
+
+       buf_len = 0;
+       for (i = 0; i < count; ++i) {
+               MonoIMTCheckItem *item = imt_entries [i];
+               if (item->is_equals) {
+                       gboolean fail_case = !item->check_target_idx && fail_tramp;
+
+                       if (item->check_target_idx || fail_case) {
+                               if (!item->compare_done || fail_case) {
+                                       buf_len += 4 * 4 + 4;
+                               }
+                               buf_len += 4;
+                               if (item->has_target_code) {
+                                       buf_len += 5 * 4;
+                               } else {
+                                       buf_len += 6 * 4;
+                               }
+                               if (fail_case) {
+                                       buf_len += 5 * 4;
+                               }
+                       } else {
+                               buf_len += 6 * 4;
+                       }
+               } else {
+                       buf_len += 6 * 4;
+               }
+       }
+
+       if (fail_tramp)
+               buf = mono_method_alloc_generic_virtual_thunk (domain, buf_len);
+       else
+               buf = mono_domain_code_reserve (domain, buf_len);
+       code = buf;
+
+       /*
+        * We are called by JITted code, which passes in the IMT argument in
+        * MONO_ARCH_RGCTX_REG (r27). We need to preserve all caller saved regs
+        * except ip0/ip1.
+        */
+       imt_reg = MONO_ARCH_RGCTX_REG;
+       for (i = 0; i < count; ++i) {
+               MonoIMTCheckItem *item = imt_entries [i];
+
+               item->code_target = code;
+
+               if (item->is_equals) {
+                       /*
+                        * Check the imt argument against item->key, if equals, jump to either
+                        * item->value.target_code or to vtable [item->value.vtable_slot].
+                        * If fail_tramp is set, jump to it if not-equals.
+                        */
+                       gboolean fail_case = !item->check_target_idx && fail_tramp;
+
+                       if (item->check_target_idx || fail_case) {
+                               /* Compare imt_reg with item->key */
+                               if (!item->compare_done || fail_case) {
+                                       // FIXME: Optimize this
+                                       code = emit_imm64 (code, ARMREG_IP0, (guint64)item->key);
+                                       arm_cmpx (code, imt_reg, ARMREG_IP0);
+                               }
+                               item->jmp_code = code;
+                               arm_bcc (code, ARMCOND_NE, 0);
+                               /* Jump to target if equals */
+                               if (item->has_target_code) {
+                                       code = emit_imm64 (code, ARMREG_IP0, (guint64)item->value.target_code);
+                                       arm_brx (code, ARMREG_IP0);
+                               } else {
+                                       guint64 imm = (guint64)&(vtable->vtable [item->value.vtable_slot]);
+
+                                       code = emit_imm64 (code, ARMREG_IP0, imm);
+                                       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 0);
+                                       arm_brx (code, ARMREG_IP0);
+                               }
+
+                               if (fail_case) {
+                                       arm_patch_rel (item->jmp_code, code, MONO_R_ARM64_BCC);
+                                       item->jmp_code = NULL;
+                                       code = emit_imm64 (code, ARMREG_IP0, (guint64)fail_tramp);
+                                       arm_brx (code, ARMREG_IP0);
+                               }
+                       } else {
+                               guint64 imm = (guint64)&(vtable->vtable [item->value.vtable_slot]);
+
+                               code = emit_imm64 (code, ARMREG_IP0, imm);
+                               arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 0);
+                               arm_brx (code, ARMREG_IP0);
+                       }
+               } else {
+                       code = emit_imm64 (code, ARMREG_IP0, (guint64)item->key);
+                       arm_cmpx (code, imt_reg, ARMREG_IP0);
+                       item->jmp_code = code;
+                       arm_bcc (code, ARMCOND_HS, 0);
+               }
+       }
+       /* Patch the branches */
+       for (i = 0; i < count; ++i) {
+               MonoIMTCheckItem *item = imt_entries [i];
+               if (item->jmp_code && item->check_target_idx)
+                       arm_patch_rel (item->jmp_code, imt_entries [item->check_target_idx]->code_target, MONO_R_ARM64_BCC);
+       }
+
+       g_assert ((code - buf) < buf_len);
+
+       mono_arch_flush_icache (buf, code - buf);
+
+       return buf;
+}
+
+GSList *
+mono_arch_get_trampolines (gboolean aot)
+{
+       return mono_arm_get_exception_trampolines (aot);
+}
+
+#else /* DISABLE_JIT */
+
+gpointer
+mono_arch_build_imt_thunk (MonoVTable *vtable, MonoDomain *domain, MonoIMTCheckItem **imt_entries, int count,
+                                                  gpointer fail_tramp)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif /* !DISABLE_JIT */
+
+#ifdef MONO_ARCH_SOFT_DEBUG_SUPPORTED
+
+void
+mono_arch_set_breakpoint (MonoJitInfo *ji, guint8 *ip)
+{
+       guint8 *code = ip;
+       guint32 native_offset = ip - (guint8*)ji->code_start;
+
+       if (ji->from_aot) {
+               SeqPointInfo *info = mono_arch_get_seq_point_info (mono_domain_get (), ji->code_start);
+
+               g_assert (native_offset % 4 == 0);
+               g_assert (info->bp_addrs [native_offset / 4] == 0);
+               info->bp_addrs [native_offset / 4] = mini_get_breakpoint_trampoline ();
+       } else {
+               /* ip points to an ldrx */
+               code += 4;
+               arm_blrx (code, ARMREG_IP0);
+               mono_arch_flush_icache (ip, code - ip);
+       }
+}
+
+void
+mono_arch_clear_breakpoint (MonoJitInfo *ji, guint8 *ip)
+{
+       guint8 *code = ip;
+
+       if (ji->from_aot) {
+               guint32 native_offset = ip - (guint8*)ji->code_start;
+               SeqPointInfo *info = mono_arch_get_seq_point_info (mono_domain_get (), ji->code_start);
+
+               g_assert (native_offset % 4 == 0);
+               info->bp_addrs [native_offset / 4] = NULL;
+       } else {
+               /* ip points to an ldrx */
+               code += 4;
+               arm_nop (code);
+               mono_arch_flush_icache (ip, code - ip);
+       }
+}
+
+void
+mono_arch_start_single_stepping (void)
+{
+       ss_trampoline = mini_get_single_step_trampoline ();
+}
+
+void
+mono_arch_stop_single_stepping (void)
+{
+       ss_trampoline = NULL;
+}
+
+gboolean
+mono_arch_is_single_step_event (void *info, void *sigctx)
+{
+       /* We use soft breakpoints on arm64 */
+       return FALSE;
+}
+
+gboolean
+mono_arch_is_breakpoint_event (void *info, void *sigctx)
+{
+       /* We use soft breakpoints on arm64 */
+       return FALSE;
+}
+
+void
+mono_arch_skip_breakpoint (MonoContext *ctx, MonoJitInfo *ji)
+{
+       g_assert_not_reached ();
+}
+
+void
+mono_arch_skip_single_step (MonoContext *ctx)
+{
+       g_assert_not_reached ();
+}
+
+gpointer
+mono_arch_get_seq_point_info (MonoDomain *domain, guint8 *code)
+{
+       SeqPointInfo *info;
+       MonoJitInfo *ji;
+
+       // FIXME: Add a free function
+
+       mono_domain_lock (domain);
+       info = g_hash_table_lookup (domain_jit_info (domain)->arch_seq_points, 
+                                                               code);
+       mono_domain_unlock (domain);
+
+       if (!info) {
+               ji = mono_jit_info_table_find (domain, (char*)code);
+               g_assert (ji);
+
+               info = g_malloc0 (sizeof (SeqPointInfo) + (ji->code_size / 4) * sizeof(guint8*));
+
+               info->ss_tramp_addr = &ss_trampoline;
+
+               mono_domain_lock (domain);
+               g_hash_table_insert (domain_jit_info (domain)->arch_seq_points,
+                                                        code, info);
+               mono_domain_unlock (domain);
+       }
+
+       return info;
+}
+
+void
+mono_arch_init_lmf_ext (MonoLMFExt *ext, gpointer prev_lmf)
+{
+       ext->lmf.previous_lmf = prev_lmf;
+       /* Mark that this is a MonoLMFExt */
+       ext->lmf.previous_lmf = (gpointer)(((gssize)ext->lmf.previous_lmf) | 2);
+       ext->lmf.gregs [MONO_ARCH_LMF_REG_SP] = (gssize)ext;
+}
+
+#endif /* MONO_ARCH_SOFT_DEBUG_SUPPORTED */
+
+gboolean
+mono_arch_opcode_supported (int opcode)
+{
+       switch (opcode) {
+       case OP_ATOMIC_ADD_I4:
+       case OP_ATOMIC_ADD_I8:
+       case OP_ATOMIC_EXCHANGE_I4:
+       case OP_ATOMIC_EXCHANGE_I8:
+       case OP_ATOMIC_CAS_I4:
+       case OP_ATOMIC_CAS_I8:
+       case OP_ATOMIC_LOAD_I1:
+       case OP_ATOMIC_LOAD_I2:
+       case OP_ATOMIC_LOAD_I4:
+       case OP_ATOMIC_LOAD_I8:
+       case OP_ATOMIC_LOAD_U1:
+       case OP_ATOMIC_LOAD_U2:
+       case OP_ATOMIC_LOAD_U4:
+       case OP_ATOMIC_LOAD_U8:
+       case OP_ATOMIC_LOAD_R4:
+       case OP_ATOMIC_LOAD_R8:
+       case OP_ATOMIC_STORE_I1:
+       case OP_ATOMIC_STORE_I2:
+       case OP_ATOMIC_STORE_I4:
+       case OP_ATOMIC_STORE_I8:
+       case OP_ATOMIC_STORE_U1:
+       case OP_ATOMIC_STORE_U2:
+       case OP_ATOMIC_STORE_U4:
+       case OP_ATOMIC_STORE_U8:
+       case OP_ATOMIC_STORE_R4:
+       case OP_ATOMIC_STORE_R8:
+               return TRUE;
+       default:
+               return FALSE;
+       }
+}
+
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
+{
+       return get_call_info (mp, sig);
+}
+
+gpointer
+mono_arch_install_handler_block_guard (MonoJitInfo *ji, MonoJitExceptionInfo *clause, MonoContext *ctx, gpointer new_value)
+{
+       gpointer *lr_loc;
+       char *old_value;
+       char *bp;
+
+       /*Load the spvar*/
+       bp = MONO_CONTEXT_GET_BP (ctx);
+       lr_loc = (gpointer*)(bp + clause->exvar_offset);
+
+       old_value = *lr_loc;
+       if ((char*)old_value < (char*)ji->code_start || (char*)old_value > ((char*)ji->code_start + ji->code_size))
+               return old_value;
+
+       *lr_loc = new_value;
+
+       return old_value;
+}
index a963c75d51c94066c43d482262b48ff4e9eb2b52..e3e90eb6ea59bd350346001e0c5c22a065e4349e 100644 (file)
@@ -1 +1,270 @@
-#include "../../../mono-extensions/mono/mini/mini-arm64.h"
+/*
+ * mini-arm64.h
+ *
+ * Copyright 2013 Xamarin Inc
+ *
+ * Based on mini-arm.h:
+ *
+ * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+#ifndef __MONO_MINI_ARM64_H__
+#define __MONO_MINI_ARM64_H__
+
+#include <mono/arch/arm64/arm64-codegen.h>
+#include <mono/mini/mini-arm64-gsharedvt.h>
+
+#define MONO_ARCH_CPU_SPEC mono_arm64_cpu_desc
+
+#define MONO_MAX_IREGS 32
+#define MONO_MAX_FREGS 32
+
+#define MONO_CONTEXT_SET_LLVM_EXC_REG(ctx, exc) do { (ctx)->regs [0] = (gsize)exc; } while (0)
+
+#define MONO_INIT_CONTEXT_FROM_FUNC(ctx,func) do {     \
+               MONO_CONTEXT_SET_BP ((ctx), __builtin_frame_address (0));       \
+               MONO_CONTEXT_SET_SP ((ctx), __builtin_frame_address (0));       \
+               MONO_CONTEXT_SET_IP ((ctx), (func));    \
+       } while (0)
+
+#define MONO_ARCH_INIT_TOP_LMF_ENTRY(lmf)
+
+/* Parameters used by the register allocator */
+/* r0..r7, r9..r14 (r15 is the imt/rgctx reg) */
+#define MONO_ARCH_CALLEE_REGS 0xfeff
+/* r19..r28 */
+#define MONO_ARCH_CALLEE_SAVED_REGS (0x3ff << 19)
+
+/* v16/v17 is reserved for a scratch reg */
+#define MONO_ARCH_CALLEE_FREGS 0xfffc00ff
+/* v8..v15 */
+#define MONO_ARCH_CALLEE_SAVED_FREGS 0xff00
+
+#define MONO_ARCH_USE_FPSTACK FALSE
+#define MONO_ARCH_FPSTACK_SIZE 0
+
+#define MONO_ARCH_INST_SREG2_MASK(ins) (0)
+
+#define MONO_ARCH_INST_FIXED_REG(desc) ((desc) == 'a' ? ARMREG_R0 : -1)
+
+#define MONO_ARCH_INST_IS_REGPAIR(desc) (0)
+
+#define MONO_ARCH_INST_IS_FLOAT(desc) ((desc) == 'f')
+
+#define MONO_ARCH_INST_REGPAIR_REG2(desc,hreg1) (-1)
+
+#define MONO_ARCH_USE_FPSTACK FALSE
+
+#define MONO_ARCH_FRAME_ALIGNMENT 16
+
+#define MONO_ARCH_CODE_ALIGNMENT 32
+
+/* callee saved regs + fp + sp */
+#define MONO_ARCH_LMF_REGS ((0x3ff << 19) | (1 << ARMREG_FP) | (1 << ARMREG_SP))
+#define MONO_ARCH_NUM_LMF_REGS (10 + 2)
+#define MONO_ARCH_FIRST_LMF_REG ARMREG_R19
+#define MONO_ARCH_LMF_REG_FP 10
+#define MONO_ARCH_LMF_REG_SP 11
+
+struct MonoLMF {
+       /* 
+        * If the second lowest bit is set to 1, then this is a MonoLMFExt structure, and
+        * the other fields are not valid.
+        */
+       gpointer    previous_lmf;
+       gpointer    lmf_addr;
+       mgreg_t    pc;
+       mgreg_t    gregs [MONO_ARCH_NUM_LMF_REGS];
+};
+
+/* Structure used by the sequence points in AOTed code */
+typedef struct {
+       gpointer ss_trigger_page;
+       gpointer bp_trigger_page;
+       gpointer ss_tramp_addr;
+       guint8* bp_addrs [MONO_ZERO_LEN_ARRAY];
+} SeqPointInfo;
+
+#define PARAM_REGS 8
+#define FP_PARAM_REGS 8
+
+#define DYN_CALL_STACK_ARGS 6
+
+typedef struct {
+       /* The +1 is for r8 */
+       mgreg_t regs [PARAM_REGS + 1 + DYN_CALL_STACK_ARGS];
+       mgreg_t res, res2;
+       guint8 *ret;
+       double fpregs [FP_PARAM_REGS];
+       int n_fpargs, n_fpret;
+       guint8 buffer [256];
+} DynCallArgs;
+
+typedef struct {
+       gpointer cinfo;
+       int saved_gregs_offset;
+       /* Points to arguments received on the stack */
+       int args_reg;
+       gboolean cond_branch_islands;
+       gpointer vret_addr_loc;
+       gpointer seq_point_info_var;
+       gpointer ss_tramp_var;
+       gpointer bp_tramp_var;
+       guint8 *thunks;
+       int thunks_size;
+} MonoCompileArch;
+
+#define MONO_ARCH_EMULATE_FREM 1
+#define MONO_ARCH_NO_EMULATE_LONG_MUL_OPTS 1
+#define MONO_ARCH_EMULATE_LONG_MUL_OVF_OPTS 1
+#define MONO_ARCH_NO_EMULATE_LONG_SHIFT_OPS 1
+#define MONO_ARCH_NEED_DIV_CHECK 1
+#define MONO_ARCH_EMULATE_MUL_OVF 1
+#define MONO_ARCH_HAVE_IMT 1
+#define MONO_ARCH_HAVE_OP_TAIL_CALL 1
+#define MONO_ARCH_THIS_AS_FIRST_ARG 1
+#define MONO_ARCH_RGCTX_REG ARMREG_R15
+#define MONO_ARCH_IMT_REG MONO_ARCH_RGCTX_REG
+#define MONO_ARCH_VTABLE_REG ARMREG_R0
+#define MONO_ARCH_EXC_REG ARMREG_R0
+#define MONO_ARCH_HAVE_XP_UNWIND 1
+#define MONO_ARCH_HAVE_CREATE_DELEGATE_TRAMPOLINE 1
+#define MONO_ARCH_HAVE_GENERALIZED_IMT_THUNK 1
+#define MONO_ARCH_USE_SIGACTION 1
+#define MONO_ARCH_HAVE_SIGCTX_TO_MONOCTX 1
+#define MONO_ARCH_HAVE_CONTEXT_SET_INT_REG 1
+#define MONO_ARCH_GSHARED_SUPPORTED 1
+#define MONO_ARCH_AOT_SUPPORTED 1
+#define MONO_ARCH_LLVM_SUPPORTED 1
+#define MONO_ARCH_HAVE_FULL_AOT_TRAMPOLINES 1
+#define MONO_ARCH_HAVE_EXCEPTIONS_INIT 1
+#define MONO_ARCH_HAVE_GET_TRAMPOLINES 1
+#define MONO_ARCH_DYN_CALL_SUPPORTED 1
+#define MONO_ARCH_DYN_CALL_PARAM_AREA (DYN_CALL_STACK_ARGS * 8)
+#define MONO_ARCH_SOFT_DEBUG_SUPPORTED 1
+#ifndef TARGET_ANDROID
+#define MONO_ARCH_GSHAREDVT_SUPPORTED 1
+#endif
+#define MONO_ARCH_HAVE_SETUP_RESUME_FROM_SIGNAL_HANDLER_CTX 1
+#define MONO_ARCH_HAVE_SETUP_ASYNC_CALLBACK 1
+#define MONO_ARCH_HAVE_GENERAL_RGCTX_LAZY_FETCH_TRAMPOLINE 1
+#ifndef MONO_CROSS_COMPILE
+#define MONO_ARCH_ENABLE_MONO_LMF_VAR 1
+#endif
+#define MONO_ARCH_HAVE_OP_GET_EX_OBJ 1
+#define MONO_ARCH_HAVE_OBJC_GET_SELECTOR 1
+#define MONO_ARCH_HAVE_SDB_TRAMPOLINES 1
+#define MONO_ARCH_HAVE_PATCH_CODE_NEW 1
+#define MONO_ARCH_HAVE_OP_GENERIC_CLASS_INIT 1
+#define MONO_ARCH_HAVE_OPCODE_NEEDS_EMULATION 1
+#define MONO_ARCH_HAVE_DECOMPOSE_LONG_OPTS 1
+#define MONO_ARCH_HAVE_HANDLER_BLOCK_GUARD 1
+
+#ifdef TARGET_IOS
+
+#define MONO_ARCH_REDZONE_SIZE 128
+
+#else
+
+#define MONO_ARCH_REDZONE_SIZE 0
+#if !defined(__PIC__)
+#define MONO_ARCH_HAVE_TLS_GET 1
+#endif
+#define MONO_ARCH_HAVE_TLS_GET_REG 1
+
+#endif
+
+#if defined(TARGET_APPLETVOS) || defined(TARGET_IOS)
+#define MONO_ARCH_HAVE_UNWIND_BACKTRACE 1
+#endif
+
+/* Relocations */
+#define MONO_R_ARM64_B 1
+#define MONO_R_ARM64_BCC 2
+#define MONO_R_ARM64_IMM 3
+#define MONO_R_ARM64_BL 4
+#define MONO_R_ARM64_BL_SHORT 5
+#define MONO_R_ARM64_CBZ 6
+
+
+typedef enum {
+       ArgInIReg,
+       ArgInFReg,
+       ArgInFRegR4,
+       ArgOnStack,
+       ArgOnStackR8,
+       ArgOnStackR4,
+       /*
+        * Vtype passed in consecutive int registers.
+        * ainfo->reg is the firs register,
+        * ainfo->nregs is the number of registers,
+        * ainfo->size is the size of the structure.
+        */
+       ArgVtypeInIRegs,
+       ArgVtypeByRef,
+       ArgVtypeByRefOnStack,
+       ArgVtypeOnStack,
+       ArgHFA,
+       ArgNone
+} ArgStorage;
+
+typedef struct {
+       ArgStorage storage;
+       int reg;
+       /* ArgOnStack */
+       int offset;
+       /* ArgVtypeInIRegs/ArgHFA */
+       int nregs, size;
+       /* ArgHFA */
+       int esize;
+       /* ArgHFA */
+       /* The offsets of the float values inside the arg */
+       guint16 foffsets [4];
+       /* ArgOnStack */
+       int slot_size;
+       /* hfa */
+       int nfregs_to_skip;
+       gboolean sign;
+       gboolean gsharedvt;
+       gboolean hfa;
+} ArgInfo;
+
+typedef struct {
+       int nargs;
+       int gr, fr, stack_usage;
+       gboolean pinvoke;
+       ArgInfo ret;
+       ArgInfo sig_cookie;
+       ArgInfo args [1];
+} CallInfo;
+
+
+guint8* mono_arm_emit_imm64 (guint8 *code, int dreg, gint64 imm);
+
+guint8* mono_arm_emit_ldrx (guint8 *code, int rt, int rn, int imm);
+
+guint8* mono_arm_emit_destroy_frame (guint8 *code, int stack_offset, guint64 temp_regs);
+
+guint8* mono_arm_emit_store_regset (guint8 *code, guint64 regs, int basereg, int offset);
+
+guint8* mono_arm_emit_store_regarray (guint8 *code, guint64 regs, int basereg, int offset);
+
+guint8* mono_arm_emit_load_regarray (guint8 *code, guint64 regs, int basereg, int offset);
+
+/* MonoJumpInfo **ji */
+guint8* mono_arm_emit_aotconst (gpointer ji, guint8 *code, guint8 *code_start, int dreg, guint32 patch_type, gconstpointer data);
+
+void mono_arm_patch (guint8 *code, guint8 *target, int relocation);
+
+void mono_arm_throw_exception (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp_regs, gboolean corlib, gboolean rethrow);
+
+void mono_arm_gsharedvt_init (void);
+
+GSList* mono_arm_get_exception_trampolines (gboolean aot);
+
+void mono_arm_resume_unwind (gpointer arg, mgreg_t pc, mgreg_t *int_regs, gdouble *fp_regs, gboolean corlib, gboolean rethrow);
+
+CallInfo* mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig);
+
+#endif /* __MONO_MINI_ARM64_H__ */
index 83170902e4ee113fe059ea27ab3cf26949af8f3d..5e5c27a53f6d21701ec85ced4cfc39c5b5132406 100644 (file)
@@ -455,15 +455,24 @@ mono_print_ji (const MonoJumpInfo *ji)
 
 void
 mono_print_ins_index (int i, MonoInst *ins)
+{
+       GString *buf = mono_print_ins_index_strbuf (i, ins);
+       printf ("%s\n", buf->str);
+       g_string_free (buf, TRUE);
+}
+
+GString *
+mono_print_ins_index_strbuf (int i, MonoInst *ins)
 {
        const char *spec = ins_get_spec (ins->opcode);
+       GString *sbuf = g_string_new (NULL);
        int num_sregs, j;
        int sregs [MONO_MAX_SRC_REGS];
 
        if (i != -1)
-               printf ("\t%-2d %s", i, mono_inst_name (ins->opcode));
+               g_string_append_printf (sbuf, "\t%-2d %s", i, mono_inst_name (ins->opcode));
        else
-               printf (" %s", mono_inst_name (ins->opcode));
+               g_string_append_printf (sbuf, " %s", mono_inst_name (ins->opcode));
        if (spec == MONO_ARCH_CPU_SPEC) {
                gboolean dest_base = FALSE;
                switch (ins->opcode) {
@@ -477,16 +486,16 @@ mono_print_ins_index (int i, MonoInst *ins)
                /* This is a lowered opcode */
                if (ins->dreg != -1) {
                        if (dest_base)
-                               printf (" [R%d + 0x%lx] <-", ins->dreg, (long)ins->inst_offset);
+                               g_string_append_printf (sbuf, " [R%d + 0x%lx] <-", ins->dreg, (long)ins->inst_offset);
                        else
-                               printf (" R%d <-", ins->dreg);
+                               g_string_append_printf (sbuf, " R%d <-", ins->dreg);
                }
                if (ins->sreg1 != -1)
-                       printf (" R%d", ins->sreg1);
+                       g_string_append_printf (sbuf, " R%d", ins->sreg1);
                if (ins->sreg2 != -1)
-                       printf (" R%d", ins->sreg2);
+                       g_string_append_printf (sbuf, " R%d", ins->sreg2);
                if (ins->sreg3 != -1)
-                       printf (" R%d", ins->sreg3);
+                       g_string_append_printf (sbuf, " R%d", ins->sreg3);
 
                switch (ins->opcode) {
                case OP_LBNE_UN:
@@ -500,39 +509,38 @@ mono_print_ins_index (int i, MonoInst *ins)
                case OP_LBLE:
                case OP_LBLE_UN:
                        if (!ins->inst_false_bb)
-                               printf (" [B%d]", ins->inst_true_bb->block_num);
+                               g_string_append_printf (sbuf, " [B%d]", ins->inst_true_bb->block_num);
                        else
-                               printf (" [B%dB%d]", ins->inst_true_bb->block_num, ins->inst_false_bb->block_num);
+                               g_string_append_printf (sbuf, " [B%dB%d]", ins->inst_true_bb->block_num, ins->inst_false_bb->block_num);
                        break;
                case OP_PHI:
                case OP_VPHI:
                case OP_XPHI:
                case OP_FPHI: {
                        int i;
-                       printf (" [%d (", (int)ins->inst_c0);
+                       g_string_append_printf (sbuf, " [%d (", (int)ins->inst_c0);
                        for (i = 0; i < ins->inst_phi_args [0]; i++) {
                                if (i)
-                                       printf (", ");
-                               printf ("R%d", ins->inst_phi_args [i + 1]);
+                                       g_string_append_printf (sbuf, ", ");
+                               g_string_append_printf (sbuf, "R%d", ins->inst_phi_args [i + 1]);
                        }
-                       printf (")]");
+                       g_string_append_printf (sbuf, ")]");
                        break;
                }
                case OP_LDADDR:
                case OP_OUTARG_VTRETADDR:
-                       printf (" R%d", ((MonoInst*)ins->inst_p0)->dreg);
+                       g_string_append_printf (sbuf, " R%d", ((MonoInst*)ins->inst_p0)->dreg);
                        break;
                case OP_REGOFFSET:
                case OP_GSHAREDVT_ARG_REGOFFSET:
-                       printf (" + 0x%lx", (long)ins->inst_offset);
+                       g_string_append_printf (sbuf, " + 0x%lx", (long)ins->inst_offset);
                        break;
                default:
                        break;
                }
 
-               printf ("\n");
                //g_error ("Unknown opcode: %s\n", mono_inst_name (ins->opcode));
-               return;
+               return sbuf;
        }
 
        if (spec [MONO_INST_DEST]) {
@@ -540,44 +548,44 @@ mono_print_ins_index (int i, MonoInst *ins)
                if (is_soft_reg (ins->dreg, bank)) {
                        if (spec [MONO_INST_DEST] == 'b') {
                                if (ins->inst_offset == 0)
-                                       printf (" [R%d] <-", ins->dreg);
+                                       g_string_append_printf (sbuf, " [R%d] <-", ins->dreg);
                                else
-                                       printf (" [R%d + 0x%lx] <-", ins->dreg, (long)ins->inst_offset);
+                                       g_string_append_printf (sbuf, " [R%d + 0x%lx] <-", ins->dreg, (long)ins->inst_offset);
                        }
                        else
-                               printf (" R%d <-", ins->dreg);
+                               g_string_append_printf (sbuf, " R%d <-", ins->dreg);
                } else if (spec [MONO_INST_DEST] == 'b') {
                        if (ins->inst_offset == 0)
-                               printf (" [%s] <-", mono_arch_regname (ins->dreg));
+                               g_string_append_printf (sbuf, " [%s] <-", mono_arch_regname (ins->dreg));
                        else
-                               printf (" [%s + 0x%lx] <-", mono_arch_regname (ins->dreg), (long)ins->inst_offset);
+                               g_string_append_printf (sbuf, " [%s + 0x%lx] <-", mono_arch_regname (ins->dreg), (long)ins->inst_offset);
                } else
-                       printf (" %s <-", mono_regname_full (ins->dreg, bank));
+                       g_string_append_printf (sbuf, " %s <-", mono_regname_full (ins->dreg, bank));
        }
        if (spec [MONO_INST_SRC1]) {
                int bank = sreg1_bank (spec);
                if (is_soft_reg (ins->sreg1, bank)) {
                        if (spec [MONO_INST_SRC1] == 'b')
-                               printf (" [R%d + 0x%lx]", ins->sreg1, (long)ins->inst_offset);
+                               g_string_append_printf (sbuf, " [R%d + 0x%lx]", ins->sreg1, (long)ins->inst_offset);
                        else
-                               printf (" R%d", ins->sreg1);
+                               g_string_append_printf (sbuf, " R%d", ins->sreg1);
                } else if (spec [MONO_INST_SRC1] == 'b')
-                       printf (" [%s + 0x%lx]", mono_arch_regname (ins->sreg1), (long)ins->inst_offset);
+                       g_string_append_printf (sbuf, " [%s + 0x%lx]", mono_arch_regname (ins->sreg1), (long)ins->inst_offset);
                else
-                       printf (" %s", mono_regname_full (ins->sreg1, bank));
+                       g_string_append_printf (sbuf, " %s", mono_regname_full (ins->sreg1, bank));
        }
        num_sregs = mono_inst_get_src_registers (ins, sregs);
        for (j = 1; j < num_sregs; ++j) {
                int bank = sreg_bank (j, spec);
                if (is_soft_reg (sregs [j], bank))
-                       printf (" R%d", sregs [j]);
+                       g_string_append_printf (sbuf, " R%d", sregs [j]);
                else
-                       printf (" %s", mono_regname_full (sregs [j], bank));
+                       g_string_append_printf (sbuf, " %s", mono_regname_full (sregs [j], bank));
        }
 
        switch (ins->opcode) {
        case OP_ICONST:
-               printf (" [%d]", (int)ins->inst_c0);
+               g_string_append_printf (sbuf, " [%d]", (int)ins->inst_c0);
                break;
 #if defined(TARGET_X86) || defined(TARGET_AMD64)
        case OP_X86_PUSH_IMM:
@@ -591,20 +599,20 @@ mono_print_ins_index (int i, MonoInst *ins)
        case OP_IXOR_IMM:
        case OP_SUB_IMM:
        case OP_STORE_MEMBASE_IMM:
-               printf (" [%d]", (int)ins->inst_imm);
+               g_string_append_printf (sbuf, " [%d]", (int)ins->inst_imm);
                break;
        case OP_ADD_IMM:
        case OP_LADD_IMM:
-               printf (" [%d]", (int)(gssize)ins->inst_p1);
+               g_string_append_printf (sbuf, " [%d]", (int)(gssize)ins->inst_p1);
                break;
        case OP_I8CONST:
-               printf (" [%lld]", (long long)ins->inst_l);
+               g_string_append_printf (sbuf, " [%lld]", (long long)ins->inst_l);
                break;
        case OP_R8CONST:
-               printf (" [%f]", *(double*)ins->inst_p0);
+               g_string_append_printf (sbuf, " [%f]", *(double*)ins->inst_p0);
                break;
        case OP_R4CONST:
-               printf (" [%f]", *(float*)ins->inst_p0);
+               g_string_append_printf (sbuf, " [%f]", *(float*)ins->inst_p0);
                break;
        case OP_CALL:
        case OP_CALL_MEMBASE:
@@ -629,22 +637,22 @@ mono_print_ins_index (int i, MonoInst *ins)
                         * JIT passes them to backends.
                         */
                        if (ins->dreg != -1)
-                               printf (" R%d <-", ins->dreg);
+                               g_string_append_printf (sbuf, " R%d <-", ins->dreg);
                }
 
                if (call->method) {
                        char *full_name = mono_method_full_name (call->method, TRUE);
-                       printf (" [%s]", full_name);
+                       g_string_append_printf (sbuf, " [%s]", full_name);
                        g_free (full_name);
                } else if (call->fptr_is_patch) {
                        MonoJumpInfo *ji = (MonoJumpInfo*)call->fptr;
 
-                       printf (" ");
+                       g_string_append_printf (sbuf, " ");
                        mono_print_ji (ji);
                } else if (call->fptr) {
                        MonoJitICallInfo *info = mono_find_jit_icall_by_addr (call->fptr);
                        if (info)
-                               printf (" [%s]", info->name);
+                               g_string_append_printf (sbuf, " [%s]", info->name);
                }
 
                list = call->out_ireg_args;
@@ -656,7 +664,7 @@ mono_print_ins_index (int i, MonoInst *ins)
                        hreg = regpair >> 24;
                        reg = regpair & 0xffffff;
 
-                       printf (" [%s <- R%d]", mono_arch_regname (hreg), reg);
+                       g_string_append_printf (sbuf, " [%s <- R%d]", mono_arch_regname (hreg), reg);
 
                        list = g_slist_next (list);
                }
@@ -669,7 +677,7 @@ mono_print_ins_index (int i, MonoInst *ins)
                        hreg = regpair >> 24;
                        reg = regpair & 0xffffff;
 
-                       printf (" [%s <- R%d]", mono_arch_fregname (hreg), reg);
+                       g_string_append_printf (sbuf, " [%s <- R%d]", mono_arch_fregname (hreg), reg);
 
                        list = g_slist_next (list);
                }
@@ -677,7 +685,7 @@ mono_print_ins_index (int i, MonoInst *ins)
        }
        case OP_BR:
        case OP_CALL_HANDLER:
-               printf (" [B%d]", ins->inst_target_bb->block_num);
+               g_string_append_printf (sbuf, " [B%d]", ins->inst_target_bb->block_num);
                break;
        case OP_IBNE_UN:
        case OP_IBEQ:
@@ -700,27 +708,57 @@ mono_print_ins_index (int i, MonoInst *ins)
        case OP_LBLE:
        case OP_LBLE_UN:
                if (!ins->inst_false_bb)
-                       printf (" [B%d]", ins->inst_true_bb->block_num);
+                       g_string_append_printf (sbuf, " [B%d]", ins->inst_true_bb->block_num);
                else
-                       printf (" [B%dB%d]", ins->inst_true_bb->block_num, ins->inst_false_bb->block_num);
+                       g_string_append_printf (sbuf, " [B%dB%d]", ins->inst_true_bb->block_num, ins->inst_false_bb->block_num);
                break;
        case OP_LIVERANGE_START:
        case OP_LIVERANGE_END:
        case OP_GC_LIVENESS_DEF:
        case OP_GC_LIVENESS_USE:
-               printf (" R%d", (int)ins->inst_c1);
+               g_string_append_printf (sbuf, " R%d", (int)ins->inst_c1);
                break;
        case OP_IL_SEQ_POINT:
        case OP_SEQ_POINT:
-               printf (" il: 0x%x%s", (int)ins->inst_imm, ins->flags & MONO_INST_NONEMPTY_STACK ? ", nonempty-stack" : "");
+               g_string_append_printf (sbuf, " il: 0x%x%s", (int)ins->inst_imm, ins->flags & MONO_INST_NONEMPTY_STACK ? ", nonempty-stack" : "");
+               break;
+       case OP_COND_EXC_EQ:
+       case OP_COND_EXC_GE:
+       case OP_COND_EXC_GT:
+       case OP_COND_EXC_LE:
+       case OP_COND_EXC_LT:
+       case OP_COND_EXC_NE_UN:
+       case OP_COND_EXC_GE_UN:
+       case OP_COND_EXC_GT_UN:
+       case OP_COND_EXC_LE_UN:
+       case OP_COND_EXC_LT_UN:
+       case OP_COND_EXC_OV:
+       case OP_COND_EXC_NO:
+       case OP_COND_EXC_C:
+       case OP_COND_EXC_NC:
+       case OP_COND_EXC_IEQ:
+       case OP_COND_EXC_IGE:
+       case OP_COND_EXC_IGT:
+       case OP_COND_EXC_ILE:
+       case OP_COND_EXC_ILT:
+       case OP_COND_EXC_INE_UN:
+       case OP_COND_EXC_IGE_UN:
+       case OP_COND_EXC_IGT_UN:
+       case OP_COND_EXC_ILE_UN:
+       case OP_COND_EXC_ILT_UN:
+       case OP_COND_EXC_IOV:
+       case OP_COND_EXC_INO:
+       case OP_COND_EXC_IC:
+       case OP_COND_EXC_INC:
+               g_string_append_printf (sbuf, " %s", ins->inst_p1);
                break;
        default:
                break;
        }
 
        if (spec [MONO_INST_CLOB])
-               printf (" clobbers: %c", spec [MONO_INST_CLOB]);
-       printf ("\n");
+               g_string_append_printf (sbuf, " clobbers: %c", spec [MONO_INST_CLOB]);
+       return sbuf;
 }
 
 static void
index dede99f3ee9abba38dbfc55a6fdfafdd2e823ee9..28e04d6d6288388a8ca141a481b7262cd1b7ea5a 100644 (file)
@@ -1,13 +1,93 @@
 #include "config.h"
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/mini/mini-cross-helpers.c"
+#include <stdio.h>
+
+#include "config.h"
+
+#include "mini.h"
+#include "tasklets.h"
+#include <mono/metadata/abi-details.h>
+
+void
+mono_dump_metadata_offsets (void);
+
+void
+mono_metadata_cross_helpers_run (void);
+
+
+static void
+mono_dump_jit_offsets (void)
+{
+#ifdef USED_CROSS_COMPILER_OFFSETS
+       g_print ("#error not using native offsets\n");
 #else
+       mono_dump_metadata_offsets ();
+
+       g_print ("#ifndef DISABLE_JIT_OFFSETS\n");
+       g_print ("#define USED_CROSS_COMPILER_OFFSETS\n");
+#define DISABLE_METADATA_OFFSETS
+#define DECL_OFFSET2(struct,field,offset) this_should_not_happen
+#define DECL_ALIGN2(type,size) this_should_not_happen
 
-void mono_cross_helpers_run (void);
+#define DECL_OFFSET(struct,field) g_print ("DECL_OFFSET2(%s,%s,%d)\n", #struct, #field, (int)MONO_STRUCT_OFFSET (struct, field));
+#define DECL_ALIGN(type)
+#define DECL_SIZE2(type,size) this_should_not_happen
+#define DECL_SIZE(type)
+#include <mono/metadata/object-offsets.h>
+
+       g_print ("#endif //disable jit check\n");
+       g_print ("#endif //cross compiler checks\n");
+       g_print ("#endif //gc check\n");
+       g_print ("#endif //os check\n");
+       g_print ("#endif //arch check\n");
+       g_print ("#endif //USED_CROSS_COMPILER_OFFSETS check\n");
+#endif
+}
 
 void
 mono_cross_helpers_run (void)
 {
-}
+#if defined (HAS_CROSS_COMPILER_OFFSETS) && !defined (MONO_CROSS_COMPILE)
+       gboolean is_broken = FALSE;
+#endif
+
+#ifndef USED_CROSS_COMPILER_OFFSETS
+       if (g_getenv ("DUMP_CROSS_OFFSETS"))
+               mono_dump_jit_offsets ();
 #endif
+       
+#if defined (HAS_CROSS_COMPILER_OFFSETS) && !defined (MONO_CROSS_COMPILE)
+       mono_metadata_cross_helpers_run ();
+
+#define DISABLE_METADATA_OFFSETS
+#define USE_CROSS_COMPILE_OFFSETS
+#define DECL_OFFSET(struct,field) this_should_not_happen_for_cross_fields
+#define DECL_OFFSET2(struct,field,offset) \
+        if ((int)G_STRUCT_OFFSET (struct, field) != offset) { \
+               g_print (#struct ":" #field " invalid struct offset %d (expected %d)\n",        \
+                       offset, \
+                       (int)G_STRUCT_OFFSET (struct, field));  \
+               is_broken = TRUE;       \
+       }
+#define DECL_ALIGN(name,type) this_should_not_happen_for_cross_align
+#define DECL_ALIGN2(name,size) \
+        if (MONO_ALIGN_ ## name != size) { \
+               g_print (#name ": invalid alignment %d (expected %d)\n",        \
+               size,   \
+               MONO_ALIGN_ ## name);   \
+               is_broken = TRUE;       \
+       }
+#define DECL_SIZE(type) this_should_not_happen_for_cross_size
+#define DECL_SIZE2(name,size) \
+        if (MONO_SIZEOF_ ## name != size) { \
+               g_print (#name ": invalid size %d (expected %d)\n",     \
+               size,   \
+               MONO_SIZEOF_ ## name);  \
+               is_broken = TRUE;       \
+       }
+
+#include <mono/metadata/object-offsets.h>
+
+       g_assert (!is_broken);
+#endif
+}
index 659075cc30a7f7297017b408d8df42eaf82f72c6..a52f5eb80d06aef3137d018ac67b0940961f8460 100644 (file)
@@ -8,7 +8,7 @@
  * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
  *
- * See LICENSE for licensing information.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <signal.h>
 #include <dlfcn.h>
 #include <AvailabilityMacros.h>
 
-#if defined (TARGET_OSX) && (MAC_OS_X_VERSION_MIN_REQUIRED <= MAC_OS_X_VERSION_10_5)
-#define NEEDS_EXCEPTION_THREAD
-#endif
-
-#ifdef NEEDS_EXCEPTION_THREAD
-
-/*
- * This code disables the CrashReporter of MacOS X by installing
- * a dummy Mach exception handler.
- */
-
-/*
- * http://darwinsource.opendarwin.org/10.4.3/xnu-792.6.22/osfmk/man/exc_server.html
- */
-extern boolean_t exc_server (mach_msg_header_t *request_msg, mach_msg_header_t *reply_msg);
-
-/*
- * The exception message
- */
-typedef struct {
-       mach_msg_base_t msg;  /* common mach message header */
-       char payload [1024];  /* opaque */
-} mach_exception_msg_t;
-
-/* The exception port */
-static mach_port_t mach_exception_port = VM_MAP_NULL;
-
-kern_return_t
-catch_exception_raise (
-       mach_port_t exception_port,
-       mach_port_t thread,
-       mach_port_t task,
-       exception_type_t exception,
-       exception_data_t code,
-       mach_msg_type_number_t code_count);
-
-/*
- * Implicitly called by exc_server. Must be public.
- *
- * http://darwinsource.opendarwin.org/10.4.3/xnu-792.6.22/osfmk/man/catch_exception_raise.html
- */
-kern_return_t
-catch_exception_raise (
-       mach_port_t exception_port,
-       mach_port_t thread,
-       mach_port_t task,
-       exception_type_t exception,
-       exception_data_t code,
-       mach_msg_type_number_t code_count)
-{
-       /* consume the exception */
-       return KERN_FAILURE;
-}
-
-/*
- * Exception thread handler.
- */
-static
-void *
-mach_exception_thread (void *arg)
-{
-       for (;;) {
-               mach_exception_msg_t request;
-               mach_exception_msg_t reply;
-               mach_msg_return_t result;
-
-               /* receive from "mach_exception_port" */
-               result = mach_msg (&request.msg.header,
-                                  MACH_RCV_MSG | MACH_RCV_LARGE,
-                                  0,
-                                  sizeof (request),
-                                  mach_exception_port,
-                                  MACH_MSG_TIMEOUT_NONE,
-                                  MACH_PORT_NULL);
-
-               g_assert (result == MACH_MSG_SUCCESS);
-
-               /* dispatch to catch_exception_raise () */
-               exc_server (&request.msg.header, &reply.msg.header);
-
-               /* send back to sender */
-               result = mach_msg (&reply.msg.header,
-                                  MACH_SEND_MSG,
-                                  reply.msg.header.msgh_size,
-                                  0,
-                                  MACH_PORT_NULL,
-                                  MACH_MSG_TIMEOUT_NONE,
-                                  MACH_PORT_NULL);
-
-               /*
-               If we try to abort the thread while delivering an exception. The port will be gone since the kernel
-               setup a send once port to deliver the resume message and thread_abort will consume it.
-               */
-               g_assert (result == MACH_MSG_SUCCESS || result == MACH_SEND_INVALID_DEST);
-       }
-       return NULL;
-}
-
-static void
-macosx_register_exception_handler (void)
-{
-       mach_port_t task;
-       pthread_attr_t attr;
-       pthread_t thread;
-
-       if (mach_exception_port != VM_MAP_NULL)
-               return;
-
-       task = mach_task_self ();
-
-       /* create the "mach_exception_port" with send & receive rights */
-       g_assert (mach_port_allocate (task, MACH_PORT_RIGHT_RECEIVE,
-                                     &mach_exception_port) == KERN_SUCCESS);
-       g_assert (mach_port_insert_right (task, mach_exception_port, mach_exception_port,
-                                         MACH_MSG_TYPE_MAKE_SEND) == KERN_SUCCESS);
-
-       /* create the exception handler thread */
-       g_assert (!pthread_attr_init (&attr));
-       g_assert (!pthread_attr_setdetachstate (&attr, PTHREAD_CREATE_DETACHED));
-       g_assert (!pthread_create (&thread, &attr, mach_exception_thread, NULL));
-       pthread_attr_destroy (&attr);
-
-       /*
-        * register "mach_exception_port" as a receiver for the
-        * EXC_BAD_ACCESS exception
-        *
-        * http://darwinsource.opendarwin.org/10.4.3/xnu-792.6.22/osfmk/man/task_set_exception_ports.html
-        */
-       g_assert (task_set_exception_ports (task, EXC_MASK_BAD_ACCESS,
-                                           mach_exception_port,
-                                           EXCEPTION_DEFAULT,
-                                           MACHINE_THREAD_STATE) == KERN_SUCCESS);
-
-       mono_gc_register_mach_exception_thread (thread);
-}
-
-#endif
-
 /* This is #define'd by Boehm GC to _GC_dlopen. */
 #undef dlopen
 
@@ -215,9 +77,6 @@ void* dlopen(const char* path, int mode);
 void
 mono_runtime_install_handlers (void)
 {
-#ifdef NEEDS_EXCEPTION_THREAD
-       macosx_register_exception_handler ();
-#endif
        mono_runtime_posix_install_handlers ();
 
        /* Snow Leopard has a horrible bug: http://openradar.appspot.com/7209349
@@ -326,7 +185,9 @@ mono_thread_state_init_from_handle (MonoThreadUnwindState *tctx, MonoThreadInfo
        state = (thread_state_t) alloca (mono_mach_arch_get_thread_state_size ());
        mctx = (mcontext_t) alloca (mono_mach_arch_get_mcontext_size ());
 
-       ret = mono_mach_arch_get_thread_state (info->native_handle, state, &num_state);
+       do {
+               ret = mono_mach_arch_get_thread_state (info->native_handle, state, &num_state);
+       } while (ret == KERN_ABORTED);
        if (ret != KERN_SUCCESS)
                return FALSE;
 
diff --git a/mono/mini/mini-exceptions-native-unwinder.c b/mono/mini/mini-exceptions-native-unwinder.c
new file mode 100644 (file)
index 0000000..08fa26b
--- /dev/null
@@ -0,0 +1,247 @@
+/*
+ * mini-exceptions-native-unwinder.c: libcorkscrew-based native unwinder
+ *
+ * Authors:
+ *   Alex Rønne Petersen (alexrp@xamarin.com)
+ *
+ * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <config.h>
+
+#include <mono/utils/mono-logger-internals.h>
+
+/*
+ * Attempt to handle native SIGSEGVs with libunwind or libcorkscrew.
+ */
+
+#ifdef HAVE_SIGNAL_H
+#include <signal.h>
+#endif
+
+#include <mono/utils/mono-signal-handler.h>
+#include "mini.h"
+
+#if defined (PLATFORM_ANDROID)
+
+#include <signal.h>
+#include <sys/types.h>
+#include <mono/utils/mono-dl.h>
+
+#define UNW_LOCAL_ONLY
+#undef _U /* ctype.h apparently defines this and it screws up the libunwind headers. */
+#include "../../external/android-libunwind/include/libunwind.h"
+#define _U 0x01
+
+#define FUNC_NAME_LENGTH 512
+#define FRAMES_TO_UNWIND 256
+
+/* Expand the SYM argument. */
+#define LOAD_SYM(DL, ERR, SYM, VAR) _LOAD_SYM(DL, ERR, SYM, VAR)
+#define _LOAD_SYM(DL, ERR, SYM, VAR) \
+       do { \
+               if ((ERR = mono_dl_symbol (DL, #SYM, (void **) &VAR))) { \
+                       mono_dl_close (DL); \
+                       return ERR; \
+               } \
+       } while (0)
+
+typedef int (*unw_init_local_t) (unw_cursor_t *, unw_context_t *);
+typedef int (*unw_get_reg_t) (unw_cursor_t *, int, unw_word_t *);
+typedef int (*unw_get_proc_name_t) (unw_cursor_t *, char *, size_t, unw_word_t *);
+typedef int (*unw_step_t) (unw_cursor_t *);
+
+static char *
+mono_extension_handle_native_sigsegv_libunwind (void *ctx, MONO_SIG_HANDLER_INFO_TYPE *info)
+{
+       char *dl_err;
+       int unw_err;
+
+       unw_init_local_t unw_init_local_fn;
+       unw_get_reg_t unw_get_reg_fn;
+       unw_get_proc_name_t unw_get_proc_name_fn;
+       unw_step_t unw_step_fn;
+
+       unw_cursor_t cursor;
+
+       size_t frames = 0;
+
+       MonoDl *dl = mono_dl_open ("libunwind.so", MONO_DL_LAZY, &dl_err);
+
+       if (!dl)
+               return dl_err;
+
+       LOAD_SYM (dl, dl_err, UNW_OBJ (init_local), unw_init_local_fn);
+       LOAD_SYM (dl, dl_err, UNW_OBJ (get_reg), unw_get_reg_fn);
+       LOAD_SYM (dl, dl_err, UNW_OBJ (get_proc_name), unw_get_proc_name_fn);
+       LOAD_SYM (dl, dl_err, UNW_OBJ (step), unw_step_fn);
+
+       if ((unw_err = unw_init_local_fn (&cursor, ctx))) {
+               mono_dl_close (dl);
+
+               return g_strdup_printf ("unw_init_local () returned %d", unw_err);
+       }
+
+       do {
+               int reg_err;
+
+               unw_word_t ip, off;
+               char name [FUNC_NAME_LENGTH];
+
+               if ((reg_err = unw_get_reg_fn (&cursor, UNW_REG_IP, &ip))) {
+                       mono_runtime_printf_err ("unw_get_reg (UNW_REG_IP) returned %d", reg_err);
+                       break;
+               }
+
+               reg_err = unw_get_proc_name_fn (&cursor, name, FUNC_NAME_LENGTH, &off);
+
+               if (reg_err == -UNW_ENOINFO)
+                       strcpy (name, "???");
+
+               mono_runtime_printf_err (" at %s+%zu [0x%zx]", name, off, ip);
+
+               unw_err = unw_step_fn (&cursor);
+               frames++;
+       } while (unw_err > 0 && frames < FRAMES_TO_UNWIND);
+
+       if (unw_err < 0)
+               mono_runtime_printf_err ("unw_step () returned %d", unw_err);
+
+       mono_dl_close (dl);
+
+       return NULL;
+}
+
+/*
+ * This code is based on the AOSP header system/core/include/corkscrew/backtrace.h.
+ *
+ * This is copied here because libcorkscrew is not a stable library and the header (and
+ * other headers that it depends on) will eventually go away.
+ *
+ * We can probably remove this one day when libunwind becomes the norm.
+ */
+
+typedef struct {
+       uintptr_t absolute_pc;
+       uintptr_t stack_top;
+       size_t stack_size;
+} backtrace_frame_t;
+
+typedef struct {
+       uintptr_t relative_pc;
+       uintptr_t relative_symbol_addr;
+       char *map_name;
+       char *symbol_name;
+       char *demangled_name;
+} backtrace_symbol_t;
+
+typedef void (*get_backtrace_symbols_t) (const backtrace_frame_t *backtrace, size_t frames, backtrace_symbol_t *backtrace_symbols);
+typedef void (*free_backtrace_symbols_t) (backtrace_symbol_t *backtrace_symbols, size_t frames);
+
+enum {
+       MAX_BACKTRACE_LINE_LENGTH = 800,
+};
+
+/* Internals that we're exploiting to work in a signal handler. Only works on ARM/x86. */
+
+typedef struct map_info_t map_info_t;
+
+typedef ssize_t (*unwind_backtrace_signal_arch_t) (siginfo_t *si, void *sc, const map_info_t *lst, backtrace_frame_t *bt, size_t ignore_depth, size_t max_depth);
+typedef map_info_t *(*acquire_my_map_info_list_t) (void);
+typedef void (*release_my_map_info_list_t) (map_info_t *milist);
+
+static char *
+mono_extension_handle_native_sigsegv_libcorkscrew (void *ctx, MONO_SIG_HANDLER_INFO_TYPE *info)
+{
+#if defined (__arm__) || defined (__i386__)
+       char *dl_err;
+
+       get_backtrace_symbols_t get_backtrace_symbols;
+       free_backtrace_symbols_t free_backtrace_symbols;
+       unwind_backtrace_signal_arch_t unwind_backtrace_signal_arch;
+       acquire_my_map_info_list_t acquire_my_map_info_list;
+       release_my_map_info_list_t release_my_map_info_list;
+
+       backtrace_frame_t frames [FRAMES_TO_UNWIND];
+       backtrace_symbol_t symbols [FRAMES_TO_UNWIND];
+
+       map_info_t *map_info;
+       ssize_t frames_unwound;
+       size_t i;
+
+       MonoDl *dl = mono_dl_open ("libcorkscrew.so", MONO_DL_LAZY, &dl_err);
+
+       if (!dl)
+               return dl_err;
+
+       LOAD_SYM (dl, dl_err, get_backtrace_symbols, get_backtrace_symbols);
+       LOAD_SYM (dl, dl_err, free_backtrace_symbols, free_backtrace_symbols);
+       LOAD_SYM (dl, dl_err, unwind_backtrace_signal_arch, unwind_backtrace_signal_arch);
+       LOAD_SYM (dl, dl_err, acquire_my_map_info_list, acquire_my_map_info_list);
+       LOAD_SYM (dl, dl_err, release_my_map_info_list, release_my_map_info_list);
+
+       map_info = acquire_my_map_info_list ();
+       frames_unwound = unwind_backtrace_signal_arch (info, ctx, map_info, frames, 0, FRAMES_TO_UNWIND);
+       release_my_map_info_list (map_info);
+
+       if (frames_unwound == -1) {
+               mono_dl_close (dl);
+
+               return g_strdup ("unwind_backtrace_signal_arch () returned -1");
+       }
+
+       get_backtrace_symbols (frames, frames_unwound, symbols);
+
+       for (i = 0; i < frames_unwound; i++) {
+               backtrace_frame_t *frame = frames + i;
+               backtrace_symbol_t *symbol = symbols + i;
+
+               const char *name = symbol->demangled_name ? symbol->demangled_name : (symbol->symbol_name ? symbol->symbol_name : "???");
+               uintptr_t off = symbol->relative_pc - symbol->relative_symbol_addr;
+               uintptr_t ip = frame->absolute_pc;
+
+               mono_runtime_printf_err ("  at %s+%zu [0x%zx]", name, off, ip);
+       }
+
+       free_backtrace_symbols (symbols, frames_unwound);
+
+       mono_dl_close (dl);
+
+       return NULL;
+#else
+       return g_strdup ("libcorkscrew is only supported on 32-bit ARM/x86");
+#endif
+}
+
+void
+mono_exception_native_unwind (void *ctx, MONO_SIG_HANDLER_INFO_TYPE *info)
+{
+       char *unwind_err, *corkscrew_err;
+
+       mono_runtime_printf_err ("\nAttempting native Android stacktrace:\n");
+
+       unwind_err = mono_extension_handle_native_sigsegv_libunwind (ctx, info);
+
+       if (unwind_err) {
+               corkscrew_err = mono_extension_handle_native_sigsegv_libcorkscrew (ctx, info);
+
+               if (corkscrew_err) {
+                       mono_runtime_printf_err ("\tCould not unwind with `libunwind.so`: %s", unwind_err);
+                       mono_runtime_printf_err ("\tCould not unwind with `libcorkscrew.so`: %s", corkscrew_err);
+                       mono_runtime_printf_err ("\n\tNo options left to get a native stacktrace :-(");
+
+                       g_free (corkscrew_err);
+               }
+
+               g_free (unwind_err);
+       }
+}
+
+#else
+
+void
+mono_exception_native_unwind (void *ctx, MONO_SIG_HANDLER_INFO_TYPE *info)
+{
+}
+
+#endif
index cde7e06bf05f165dced94e47bf0cf5f544aebee0..a4d15fa4849100f30054a6e2324dc540937f0aa9 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2001-2003 Ximian, Inc.
  * Copyright 2003-2008 Novell, Inc.
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com).
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
 #include "mini-llvm-cpp.h"
 #endif
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/mini/mini-exceptions.c"
-#endif
-
 #ifndef MONO_ARCH_CONTEXT_DEF
 #define MONO_ARCH_CONTEXT_DEF
 #endif
@@ -712,12 +709,16 @@ ves_icall_get_trace (MonoException *exc, gint32 skip, MonoBoolean need_file_info
 
        if (ta == NULL) {
                /* Exception is not thrown yet */
-               return mono_array_new (domain, mono_defaults.stack_frame_class, 0);
+               res = mono_array_new_checked (domain, mono_defaults.stack_frame_class, 0, &error);
+               mono_error_set_pending_exception (&error);
+               return res;
        }
 
        len = mono_array_length (ta) >> 1;
 
-       res = mono_array_new (domain, mono_defaults.stack_frame_class, len > skip ? len - skip : 0);
+       res = mono_array_new_checked (domain, mono_defaults.stack_frame_class, len > skip ? len - skip : 0, &error);
+       if (mono_error_set_pending_exception (&error))
+               return NULL;
 
        for (i = skip; i < len; i++) {
                MonoJitInfo *ji;
@@ -1281,8 +1282,9 @@ wrap_non_exception_throws (MonoMethod *m)
 
 #define MAX_UNMANAGED_BACKTRACE 128
 static MonoArray*
-build_native_trace (void)
+build_native_trace (MonoError *error)
 {
+       mono_error_init (error);
 /* This puppy only makes sense on mobile, IOW, ARM. */
 #if defined (HAVE_BACKTRACE_SYMBOLS) && defined (TARGET_ARM)
        MonoArray *res;
@@ -1292,7 +1294,8 @@ build_native_trace (void)
 
        if (!size)
                return NULL;
-       res = mono_array_new (mono_domain_get (), mono_defaults.int_class, size);
+       res = mono_array_new_checked (mono_domain_get (), mono_defaults.int_class, size, error);
+       return_val_if_nok (error, NULL);
 
        for (i = 0; i < size; i++)
                mono_array_set (res, gpointer, i, native_trace [i]);
@@ -1307,8 +1310,12 @@ setup_stack_trace (MonoException *mono_ex, GSList *dynamic_methods, MonoArray *i
 {
        if (mono_ex && !initial_trace_ips) {
                *trace_ips = g_list_reverse (*trace_ips);
-               MONO_OBJECT_SETREF (mono_ex, trace_ips, mono_glist_to_array (*trace_ips, mono_defaults.int_class));
-               MONO_OBJECT_SETREF (mono_ex, native_trace_ips, build_native_trace ());
+               MonoError error;
+               MonoArray *ips_arr = mono_glist_to_array (*trace_ips, mono_defaults.int_class, &error);
+               mono_error_assert_ok (&error);
+               MONO_OBJECT_SETREF (mono_ex, trace_ips, ips_arr);
+               MONO_OBJECT_SETREF (mono_ex, native_trace_ips, build_native_trace (&error));
+               mono_error_assert_ok (&error);
                if (dynamic_methods) {
                        /* These methods could go away anytime, so save a reference to them in the exception object */
                        GSList *l;
@@ -1348,6 +1355,7 @@ setup_stack_trace (MonoException *mono_ex, GSList *dynamic_methods, MonoArray *i
 static gboolean
 mono_handle_exception_internal_first_pass (MonoContext *ctx, MonoObject *obj, gint32 *out_filter_idx, MonoJitInfo **out_ji, MonoJitInfo **out_prev_ji, MonoObject *non_exception)
 {
+       MonoError error;
        MonoDomain *domain = mono_domain_get ();
        MonoJitInfo *ji = NULL;
        static int (*call_filter) (MonoContext *, gpointer) = NULL;
@@ -1373,10 +1381,11 @@ mono_handle_exception_internal_first_pass (MonoContext *ctx, MonoObject *obj, gi
        mono_ex = (MonoException*)obj;
        initial_trace_ips = mono_ex->trace_ips;
 
-       if (mono_object_isinst (obj, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (obj, mono_defaults.exception_class, &error)) {
                mono_ex = (MonoException*)obj;
                initial_trace_ips = mono_ex->trace_ips;
        } else {
+               mono_error_assert_ok (&error);
                mono_ex = NULL;
        }
 
@@ -1539,7 +1548,7 @@ mono_handle_exception_internal_first_pass (MonoContext *ctx, MonoObject *obj, gi
                                        }
                                }
 
-                               if (ei->flags == MONO_EXCEPTION_CLAUSE_NONE && mono_object_isinst (ex_obj, catch_class)) {
+                               if (ei->flags == MONO_EXCEPTION_CLAUSE_NONE && mono_object_isinst_checked (ex_obj, catch_class, &error)) {
                                        setup_stack_trace (mono_ex, dynamic_methods, initial_trace_ips, &trace_ips);
                                        g_slist_free (dynamic_methods);
 
@@ -1550,6 +1559,7 @@ mono_handle_exception_internal_first_pass (MonoContext *ctx, MonoObject *obj, gi
                                        MONO_CONTEXT_SET_IP (ctx, ei->handler_start);
                                        return TRUE;
                                }
+                               mono_error_cleanup (&error);
                        }
                }
 
@@ -1605,7 +1615,8 @@ mono_handle_exception_internal (MonoContext *ctx, MonoObject *obj, gboolean resu
                obj = (MonoObject *)mono_get_exception_null_reference ();
        }
 
-       if (!mono_object_isinst (obj, mono_defaults.exception_class)) {
+       if (!mono_object_isinst_checked (obj, mono_defaults.exception_class, &error)) {
+               mono_error_assert_ok (&error);
                non_exception = obj;
                obj = (MonoObject *)mono_get_exception_runtime_wrapped_checked (obj, &error);
                mono_error_assert_ok (&error);
@@ -1619,9 +1630,10 @@ mono_handle_exception_internal (MonoContext *ctx, MonoObject *obj, gboolean resu
                        ;
        }
 
-       if (mono_object_isinst (obj, mono_defaults.exception_class)) {
+       if (mono_object_isinst_checked (obj, mono_defaults.exception_class, &error)) {
                mono_ex = (MonoException*)obj;
        } else {
+               mono_error_assert_ok (&error);
                mono_ex = NULL;
        }
 
@@ -1832,8 +1844,9 @@ mono_handle_exception_internal (MonoContext *ctx, MonoObject *obj, gboolean resu
                                        filter_idx ++;
                                }
 
+                               mono_error_init (&error);
                                if ((ei->flags == MONO_EXCEPTION_CLAUSE_NONE && 
-                                        mono_object_isinst (ex_obj, catch_class)) || filtered) {
+                                    mono_object_isinst_checked (ex_obj, catch_class, &error)) || filtered) {
                                        /*
                                         * This guards against the situation that we abort a thread that is executing a finally clause
                                         * that was called by the EH machinery. It won't have a guard trampoline installed, so we must
@@ -1884,6 +1897,7 @@ mono_handle_exception_internal (MonoContext *ctx, MonoObject *obj, gboolean resu
 
                                        return 0;
                                }
+                               mono_error_cleanup (&error);
                                if (ei->flags == MONO_EXCEPTION_CLAUSE_FAULT) {
                                        if (mono_trace_is_enabled () && mono_trace_eval (method))
                                                g_print ("EXCEPTION: fault clause %d of %s\n", i, mono_method_full_name (method, TRUE));
@@ -2393,8 +2407,8 @@ mono_handle_native_sigsegv (int signal, void *ctx, MONO_SIG_HANDLER_INFO_TYPE *i
        }
 #endif
  }
-#elif defined (ENABLE_EXTENSION_MODULE)
-       mono_extension_handle_native_sigsegv (ctx, info);
+#else
+       mono_exception_native_unwind (ctx, info);
 #endif
 
        /*
@@ -2882,7 +2896,8 @@ throw_exception (MonoObject *ex, gboolean rethrow)
        MonoJitTlsData *jit_tls = mono_get_jit_tls ();
        MonoException *mono_ex;
 
-       if (!mono_object_isinst (ex, mono_defaults.exception_class)) {
+       if (!mono_object_isinst_checked (ex, mono_defaults.exception_class, &error)) {
+               mono_error_assert_ok (&error);
                mono_ex = mono_get_exception_runtime_wrapped_checked (ex, &error);
                mono_error_assert_ok (&error);
        }
@@ -2905,7 +2920,9 @@ throw_exception (MonoObject *ex, gboolean rethrow)
                        trace = g_list_append (trace, l->data);
                        trace = g_list_append (trace, NULL);
                }
-               MONO_OBJECT_SETREF (mono_ex, trace_ips, mono_glist_to_array (trace, mono_defaults.int_class));
+               MonoArray *ips_arr = mono_glist_to_array (trace, mono_defaults.int_class, &error);
+               mono_error_assert_ok (&error);
+               MONO_OBJECT_SETREF (mono_ex, trace_ips, ips_arr);
                g_list_free (l);
                g_list_free (trace);
 #endif
@@ -2962,6 +2979,7 @@ mono_llvm_resume_exception (void)
 MonoObject *
 mono_llvm_load_exception (void)
 {
+               MonoError error;
        MonoJitTlsData *jit_tls = mono_get_jit_tls ();
 
        MonoException *mono_ex = (MonoException*)mono_gchandle_get_target (jit_tls->thrown_exc);
@@ -2985,14 +3003,18 @@ mono_llvm_load_exception (void)
                // FIXME: Does this work correctly for rethrows?
                // We may be discarding useful information
                // when this gets GC'ed
-               MONO_OBJECT_SETREF (mono_ex, trace_ips, mono_glist_to_array (trace_ips, mono_defaults.int_class));
+               MonoArray *ips_arr = mono_glist_to_array (trace_ips, mono_defaults.int_class, &error);
+               mono_error_assert_ok (&error);
+               MONO_OBJECT_SETREF (mono_ex, trace_ips, ips_arr);
                g_list_free (trace_ips);
 
                // FIXME:
                //MONO_OBJECT_SETREF (mono_ex, stack_trace, ves_icall_System_Exception_get_trace (mono_ex));
        } else {
-               MONO_OBJECT_SETREF (mono_ex, trace_ips, mono_array_new (mono_domain_get (), mono_defaults.int_class, 0));
-               MONO_OBJECT_SETREF (mono_ex, stack_trace, mono_array_new (mono_domain_get (), mono_defaults.stack_frame_class, 0));
+               MONO_OBJECT_SETREF (mono_ex, trace_ips, mono_array_new_checked (mono_domain_get (), mono_defaults.int_class, 0, &error));
+               mono_error_assert_ok (&error);
+               MONO_OBJECT_SETREF (mono_ex, stack_trace, mono_array_new_checked (mono_domain_get (), mono_defaults.stack_frame_class, 0, &error));
+               mono_error_assert_ok (&error);
        }
 
        return &mono_ex->object;
@@ -3022,6 +3044,7 @@ mono_llvm_clear_exception (void)
 gint32
 mono_llvm_match_exception (MonoJitInfo *jinfo, guint32 region_start, guint32 region_end, gpointer rgctx, MonoObject *this_obj)
 {
+                       MonoError error;
        MonoJitTlsData *jit_tls = mono_get_jit_tls ();
        MonoObject *exc;
        gint32 index = -1;
@@ -3037,7 +3060,6 @@ mono_llvm_match_exception (MonoJitInfo *jinfo, guint32 region_start, guint32 reg
 
                catch_class = ei->data.catch_class;
                if (catch_class->byval_arg.type == MONO_TYPE_VAR || catch_class->byval_arg.type == MONO_TYPE_MVAR || catch_class->byval_arg.type == MONO_TYPE_GENERICINST) {
-                       MonoError error;
                        MonoGenericContext context;
                        MonoType *inflated_type;
 
@@ -3051,10 +3073,13 @@ mono_llvm_match_exception (MonoJitInfo *jinfo, guint32 region_start, guint32 reg
                }
 
                // FIXME: Handle edge cases handled in get_exception_catch_class
-               if (ei->flags == MONO_EXCEPTION_CLAUSE_NONE && mono_object_isinst (exc, catch_class)) {
+               if (ei->flags == MONO_EXCEPTION_CLAUSE_NONE && mono_object_isinst_checked (exc, catch_class, &error)) {
                        index = ei->clause_index;
                        break;
-               } else if (ei->flags == MONO_EXCEPTION_CLAUSE_FILTER) {
+               } else
+                       mono_error_assert_ok (&error);
+               
+               if (ei->flags == MONO_EXCEPTION_CLAUSE_FILTER) {
                        g_assert_not_reached ();
                }
        }
index 47265e1d10f50156070c8372ba7447619fb12436..f50d686347e2102ed79bba2a89bed8ec186244cf 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2009 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index cba6d8e7ac92b6fc1aeedb0fba64f6455c2cef49..1c37f38d726df2839d8fe82a9172edf7c47f2962 100644 (file)
@@ -1,11 +1,12 @@
 /*
- * generic-sharing.c: Support functions for generic sharing.
+ * mini-generic-sharing.c: Support functions for generic sharing.
  *
  * Author:
  *   Mark Probst (mark.probst@gmail.com)
  *
  * Copyright 2007-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -2485,11 +2486,6 @@ mono_method_lookup_rgctx (MonoVTable *class_vtable, MonoGenericInst *method_inst
        return mrgctx;
 }
 
-
-static gboolean
-generic_inst_is_sharable (MonoGenericInst *inst, gboolean allow_type_vars,
-                                                 gboolean allow_partial);
-
 static gboolean
 type_is_sharable (MonoType *type, gboolean allow_type_vars, gboolean allow_partial)
 {
@@ -2510,9 +2506,9 @@ type_is_sharable (MonoType *type, gboolean allow_type_vars, gboolean allow_parti
        if (allow_partial && !type->byref && type->type == MONO_TYPE_GENERICINST && MONO_TYPE_ISSTRUCT (type)) {
                MonoGenericClass *gclass = type->data.generic_class;
 
-               if (gclass->context.class_inst && !generic_inst_is_sharable (gclass->context.class_inst, allow_type_vars, allow_partial))
+               if (gclass->context.class_inst && !mini_generic_inst_is_sharable (gclass->context.class_inst, allow_type_vars, allow_partial))
                        return FALSE;
-               if (gclass->context.method_inst && !generic_inst_is_sharable (gclass->context.method_inst, allow_type_vars, allow_partial))
+               if (gclass->context.method_inst && !mini_generic_inst_is_sharable (gclass->context.method_inst, allow_type_vars, allow_partial))
                        return FALSE;
                if (mono_class_is_nullable (mono_class_from_mono_type (type)))
                        return FALSE;
@@ -2522,8 +2518,8 @@ type_is_sharable (MonoType *type, gboolean allow_type_vars, gboolean allow_parti
        return FALSE;
 }
 
-static gboolean
-generic_inst_is_sharable (MonoGenericInst *inst, gboolean allow_type_vars,
+gboolean
+mini_generic_inst_is_sharable (MonoGenericInst *inst, gboolean allow_type_vars,
                                                  gboolean allow_partial)
 {
        int i;
@@ -2572,10 +2568,10 @@ mono_generic_context_is_sharable_full (MonoGenericContext *context,
 {
        g_assert (context->class_inst || context->method_inst);
 
-       if (context->class_inst && !generic_inst_is_sharable (context->class_inst, allow_type_vars, allow_partial))
+       if (context->class_inst && !mini_generic_inst_is_sharable (context->class_inst, allow_type_vars, allow_partial))
                return FALSE;
 
-       if (context->method_inst && !generic_inst_is_sharable (context->method_inst, allow_type_vars, allow_partial))
+       if (context->method_inst && !mini_generic_inst_is_sharable (context->method_inst, allow_type_vars, allow_partial))
                return FALSE;
 
        return TRUE;
@@ -2643,8 +2639,6 @@ mini_method_is_open (MonoMethod *method)
 
 /* Lazy class loading functions */
 static GENERATE_TRY_GET_CLASS_WITH_CACHE (iasync_state_machine, System.Runtime.CompilerServices, IAsyncStateMachine)
-static GENERATE_TRY_GET_CLASS_WITH_CACHE (async_state_machine_attribute, System.Runtime.CompilerServices, AsyncStateMachineAttribute)
-
 
 static G_GNUC_UNUSED gboolean
 is_async_state_machine_class (MonoClass *klass)
@@ -2863,7 +2857,6 @@ mono_method_construct_object_context (MonoMethod *method)
 }
 
 static gboolean gshared_supported;
-static gboolean gsharedvt_supported;
 
 void
 mono_set_generic_sharing_supported (gboolean supported)
@@ -2871,11 +2864,6 @@ mono_set_generic_sharing_supported (gboolean supported)
        gshared_supported = supported;
 }
 
-void
-mono_set_generic_sharing_vt_supported (gboolean supported)
-{
-       gsharedvt_supported = supported;
-}
 
 void
 mono_set_partial_sharing_supported (gboolean supported)
@@ -3385,7 +3373,7 @@ get_shared_inst (MonoGenericInst *inst, MonoGenericInst *shared_inst, MonoGeneri
                if (all_vt || gsharedvt) {
                        type_argv [i] = get_gsharedvt_type (shared_inst->type_argv [i]);
                } else {
-                       /* These types match the ones in generic_inst_is_sharable () */
+                       /* These types match the ones in mini_generic_inst_is_sharable () */
                        type_argv [i] = get_shared_type (shared_inst->type_argv [i], inst->type_argv [i]);
                }
        }
@@ -3529,10 +3517,242 @@ mini_get_rgctx_entry_slot (MonoJumpInfoRgctxEntry *entry)
        return slot;
 }
 
-#if defined(ENABLE_GSHAREDVT)
+static gboolean gsharedvt_supported;
+
+void
+mono_set_generic_sharing_vt_supported (gboolean supported)
+{
+       gsharedvt_supported = supported;
+}
+
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+/*
+ * mini_is_gsharedvt_type:
+ *
+ *   Return whenever T references type arguments instantiated with gshared vtypes.
+ */
+gboolean
+mini_is_gsharedvt_type (MonoType *t)
+{
+       int i;
+
+       if (t->byref)
+               return FALSE;
+       if ((t->type == MONO_TYPE_VAR || t->type == MONO_TYPE_MVAR) && t->data.generic_param->gshared_constraint && t->data.generic_param->gshared_constraint->type == MONO_TYPE_VALUETYPE)
+               return TRUE;
+       else if (t->type == MONO_TYPE_GENERICINST) {
+               MonoGenericClass *gclass = t->data.generic_class;
+               MonoGenericContext *context = &gclass->context;
+               MonoGenericInst *inst;
+
+               inst = context->class_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (mini_is_gsharedvt_type (inst->type_argv [i]))
+                                       return TRUE;
+               }
+               inst = context->method_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (mini_is_gsharedvt_type (inst->type_argv [i]))
+                                       return TRUE;
+               }
+
+               return FALSE;
+       } else {
+               return FALSE;
+       }
+}
+
+gboolean
+mini_is_gsharedvt_klass (MonoClass *klass)
+{
+       return mini_is_gsharedvt_type (&klass->byval_arg);
+}
+
+gboolean
+mini_is_gsharedvt_signature (MonoMethodSignature *sig)
+{
+       int i;
+
+       if (sig->ret && mini_is_gsharedvt_type (sig->ret))
+               return TRUE;
+       for (i = 0; i < sig->param_count; ++i) {
+               if (mini_is_gsharedvt_type (sig->params [i]))
+                       return TRUE;
+       }
+       return FALSE;
+}
+
+/*
+ * mini_is_gsharedvt_variable_type:
+ *
+ *   Return whenever T refers to a GSHAREDVT type whose size differs depending on the values of type parameters.
+ */
+gboolean
+mini_is_gsharedvt_variable_type (MonoType *t)
+{
+       if (!mini_is_gsharedvt_type (t))
+               return FALSE;
+       if (t->type == MONO_TYPE_GENERICINST) {
+               MonoGenericClass *gclass = t->data.generic_class;
+               MonoGenericContext *context = &gclass->context;
+               MonoGenericInst *inst;
+               int i;
+
+               if (t->data.generic_class->container_class->byval_arg.type != MONO_TYPE_VALUETYPE || t->data.generic_class->container_class->enumtype)
+                       return FALSE;
 
-#include "../../../mono-extensions/mono/mini/mini-generic-sharing-gsharedvt.c"
+               inst = context->class_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (mini_is_gsharedvt_variable_type (inst->type_argv [i]))
+                                       return TRUE;
+               }
+               inst = context->method_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (mini_is_gsharedvt_variable_type (inst->type_argv [i]))
+                                       return TRUE;
+               }
 
+               return FALSE;
+       }
+       return TRUE;
+}
+
+static gboolean
+is_variable_size (MonoType *t)
+{
+       int i;
+
+       if (t->byref)
+               return FALSE;
+
+       if (t->type == MONO_TYPE_VAR || t->type == MONO_TYPE_MVAR) {
+               MonoGenericParam *param = t->data.generic_param;
+
+               if (param->gshared_constraint && param->gshared_constraint->type != MONO_TYPE_VALUETYPE && param->gshared_constraint->type != MONO_TYPE_GENERICINST)
+                       return FALSE;
+               if (param->gshared_constraint && param->gshared_constraint->type == MONO_TYPE_GENERICINST)
+                       return is_variable_size (param->gshared_constraint);
+               return TRUE;
+       }
+       if (t->type == MONO_TYPE_GENERICINST && t->data.generic_class->container_class->byval_arg.type == MONO_TYPE_VALUETYPE) {
+               MonoGenericClass *gclass = t->data.generic_class;
+               MonoGenericContext *context = &gclass->context;
+               MonoGenericInst *inst;
+
+               inst = context->class_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (is_variable_size (inst->type_argv [i]))
+                                       return TRUE;
+               }
+               inst = context->method_inst;
+               if (inst) {
+                       for (i = 0; i < inst->type_argc; ++i)
+                               if (is_variable_size (inst->type_argv [i]))
+                                       return TRUE;
+               }
+       }
+
+       return FALSE;
+}
+
+gboolean
+mini_is_gsharedvt_sharable_inst (MonoGenericInst *inst)
+{
+       int i;
+       gboolean has_vt = FALSE;
+
+       for (i = 0; i < inst->type_argc; ++i) {
+               MonoType *type = inst->type_argv [i];
+
+               if ((MONO_TYPE_IS_REFERENCE (type) || type->type == MONO_TYPE_VAR || type->type == MONO_TYPE_MVAR) && !mini_is_gsharedvt_type (type)) {
+               } else {
+                       has_vt = TRUE;
+               }
+       }
+
+       return has_vt;
+}
+
+gboolean
+mini_is_gsharedvt_sharable_method (MonoMethod *method)
+{
+       MonoMethodSignature *sig;
+
+       /*
+        * A method is gsharedvt if:
+        * - it has type parameters instantiated with vtypes
+        */
+       if (!gsharedvt_supported)
+               return FALSE;
+       if (method->is_inflated) {
+               MonoMethodInflated *inflated = (MonoMethodInflated*)method;
+               MonoGenericContext *context = &inflated->context;
+               MonoGenericInst *inst;
+
+               if (context->class_inst && context->method_inst) {
+                       /* At least one inst has to be gsharedvt sharable, and the other normal or gsharedvt sharable */
+                       gboolean vt1 = mini_is_gsharedvt_sharable_inst (context->class_inst);
+                       gboolean vt2 = mini_is_gsharedvt_sharable_inst (context->method_inst);
+
+                       if ((vt1 && vt2) ||
+                               (vt1 && mini_generic_inst_is_sharable (context->method_inst, TRUE, FALSE)) ||
+                               (vt2 && mini_generic_inst_is_sharable (context->class_inst, TRUE, FALSE)))
+                               ;
+                       else
+                               return FALSE;
+               } else {
+                       inst = context->class_inst;
+                       if (inst && !mini_is_gsharedvt_sharable_inst (inst))
+                               return FALSE;
+                       inst = context->method_inst;
+                       if (inst && !mini_is_gsharedvt_sharable_inst (inst))
+                               return FALSE;
+               }
+       } else {
+               return FALSE;
+       }
+
+       sig = mono_method_signature (mono_method_get_declaring_generic_method (method));
+       if (!sig)
+               return FALSE;
+
+       /*
+       if (mini_is_gsharedvt_variable_signature (sig))
+               return FALSE;
+       */
+
+       //DEBUG ("GSHAREDVT SHARABLE: %s\n", mono_method_full_name (method, TRUE));
+
+       return TRUE;
+}
+
+/*
+ * mini_is_gsharedvt_variable_signature:
+ *
+ *   Return whenever the calling convention used to call SIG varies depending on the values of type parameters used by SIG,
+ * i.e. FALSE for swap(T[] arr, int i, int j), TRUE for T get_t ().
+ */
+gboolean
+mini_is_gsharedvt_variable_signature (MonoMethodSignature *sig)
+{
+       int i;
+
+       if (sig->ret && is_variable_size (sig->ret))
+               return TRUE;
+       for (i = 0; i < sig->param_count; ++i) {
+               MonoType *t = sig->params [i];
+
+               if (is_variable_size (t))
+                       return TRUE;
+       }
+       return FALSE;
+}
 #else
 
 gboolean
@@ -3571,4 +3791,4 @@ mini_is_gsharedvt_variable_signature (MonoMethodSignature *sig)
        return FALSE;
 }
 
-#endif /* !MONOTOUCH */
+#endif /* !MONO_ARCH_GSHAREDVT_SUPPORTED */
index 8122365cab91355de3aada21aef334d32c2b4dc8..e3219686ae2cf5beb7eb8ea5adb7fc9987e51d86 100644 (file)
@@ -3,6 +3,7 @@
 //
 // (C) 2009-2011 Novell, Inc.
 // Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 //
index 9e8596e7bf135c3a31b057172fff8588306cdbb7..d6e2677cd237c65c788902a67174e02c426ce9d9 100644 (file)
@@ -3,6 +3,7 @@
  *
  * Copyright 2009-2011 Novell Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mini.h"
@@ -24,8 +25,6 @@
 #define __STDC_CONSTANT_MACROS
 #endif
 
-#include "llvm-c/Core.h"
-#include "llvm-c/ExecutionEngine.h"
 #include "llvm-c/BitWriter.h"
 #include "llvm-c/Analysis.h"
 
@@ -2070,6 +2069,11 @@ emit_cond_system_exception (EmitContext *ctx, MonoBasicBlock *bb, const char *ex
        MonoClass *exc_class;
        LLVMValueRef args [2];
        LLVMValueRef callee;
+       gboolean no_pc = FALSE;
+
+       if (IS_TARGET_AMD64)
+               /* Some platforms don't require the pc argument */
+               no_pc = TRUE;
        
        ex_bb = gen_bb (ctx, "EX_BB");
        if (ctx->llvm_only)
@@ -2114,7 +2118,10 @@ emit_cond_system_exception (EmitContext *ctx, MonoBasicBlock *bb, const char *ex
                LLVMTypeRef sig;
                const char *icall_name;
 
-               sig = LLVMFunctionType2 (LLVMVoidType (), LLVMInt32Type (), LLVMPointerType (LLVMInt8Type (), 0), FALSE);
+               if (no_pc)
+                       sig = LLVMFunctionType1 (LLVMVoidType (), LLVMInt32Type (), FALSE);
+               else
+                       sig = LLVMFunctionType2 (LLVMVoidType (), LLVMInt32Type (), LLVMPointerType (LLVMInt8Type (), 0), FALSE);
                icall_name = "llvm_throw_corlib_exception_abs_trampoline";
 
                if (ctx->cfg->compile_aot) {
@@ -2146,17 +2153,18 @@ emit_cond_system_exception (EmitContext *ctx, MonoBasicBlock *bb, const char *ex
                }
        }
 
-       if (IS_TARGET_X86 || IS_TARGET_AMD64)
-               args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token - MONO_TOKEN_TYPE_DEF, FALSE);
-       else
-               args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token, FALSE);
+       args [0] = LLVMConstInt (LLVMInt32Type (), exc_class->type_token - MONO_TOKEN_TYPE_DEF, FALSE);
 
        /*
         * The LLVM mono branch contains changes so a block address can be passed as an
         * argument to a call.
         */
-       args [1] = LLVMBlockAddress (ctx->lmethod, ex_bb);
-       emit_call (ctx, bb, &builder, callee, args, 2);
+       if (no_pc) {
+               emit_call (ctx, bb, &builder, callee, args, 1);
+       } else {
+               args [1] = LLVMBlockAddress (ctx->lmethod, ex_bb);
+               emit_call (ctx, bb, &builder, callee, args, 2);
+       }
 
        LLVMBuildUnreachable (builder);
 
@@ -3140,7 +3148,7 @@ process_call (EmitContext *ctx, MonoBasicBlock *bb, LLVMBuilderRef *builder_ref,
        gboolean is_virtual, calli, preserveall;
        LLVMBuilderRef builder = *builder_ref;
 
-       if (call->signature->call_convention != MONO_CALL_DEFAULT) {
+       if ((call->signature->call_convention != MONO_CALL_DEFAULT) && !((call->signature->call_convention == MONO_CALL_C) && ctx->llvm_only)) {
                set_failure (ctx, "non-default callconv");
                return;
        }
index 9dadbc30a5dc24609231c554e99a53ca26d78671..9ce9be8a98c08ce51866bafee0324a087b8ee4c0 100644 (file)
+/*
+ * magic-types.c: intrinsics for variable sized int/floats
+ *
+ * Author:
+ *   Rodrigo Kumpera (kumpera@gmail.com)
+ *
+ * (C) 2013 Xamarin
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
 #include <config.h>
+#include <stdio.h>
+
+#include "mini.h"
+#include "ir-emit.h"
+#include "glib.h"
+
+
+typedef struct {
+       const char *op_name;
+       short op_table[4];
+} IntIntrisic;
+
+typedef struct {
+       short op_index;
+       short big_stack_type;
+       short small_stack_type;
+       short stack_type;
+       short conv_4_to_8;
+       short conv_8_to_4;
+       short move;
+       short inc_op;
+       short dec_op;
+       short store_op;
+       short compare_op;
+} MagicTypeInfo;
+
 
-#if defined(MONO_NATIVE_TYPES)
+#if SIZEOF_VOID_P == 8
+#define OP_PT_ADD OP_LADD
+#define OP_PT_SUB OP_LSUB
+#define OP_PT_MUL OP_LMUL
+#define OP_PT_DIV OP_LDIV
+#define OP_PT_REM OP_LREM
+#define OP_PT_NEG OP_LNEG
+#define OP_PT_AND OP_LAND
+#define OP_PT_OR OP_LOR
+#define OP_PT_XOR OP_LXOR
+#define OP_PT_NOT OP_LNOT
+#define OP_PT_SHL OP_LSHL
+#define OP_PT_SHR OP_LSHR
 
-#include "../../../mono-extensions/mono/mini/mini-native-types.c"
+#define OP_PT_DIV_UN OP_LDIV_UN
+#define OP_PT_REM_UN OP_LREM_UN
+#define OP_PT_SHR_UN OP_LSHR_UN
+
+#define OP_PT_ADD_IMM OP_LADD_IMM
+#define OP_PT_SUB_IMM OP_LSUB_IMM
+
+#define OP_PT_STORE_FP_MEMBASE_REG OP_STORER8_MEMBASE_REG
+
+#define OP_PCOMPARE OP_LCOMPARE
 
 #else
+#define OP_PT_ADD OP_IADD
+#define OP_PT_SUB OP_ISUB
+#define OP_PT_MUL OP_IMUL
+#define OP_PT_DIV OP_IDIV
+#define OP_PT_REM OP_IREM
+#define OP_PT_NEG OP_INEG
+#define OP_PT_AND OP_IAND
+#define OP_PT_OR OP_IOR
+#define OP_PT_XOR OP_IXOR
+#define OP_PT_NOT OP_INOT
+#define OP_PT_SHL OP_ISHL
+#define OP_PT_SHR OP_ISHR
 
-#include "mini.h"
+#define OP_PT_DIV_UN OP_IDIV_UN
+#define OP_PT_REM_UN OP_IREM_UN
+#define OP_PT_SHR_UN OP_ISHR_UN
 
-MonoType*
-mini_native_type_replace_type (MonoType *type)
+#define OP_PT_ADD_IMM OP_IADD_IMM
+#define OP_PT_SUB_IMM OP_ISUB_IMM
+
+#define OP_PT_STORE_FP_MEMBASE_REG OP_STORER4_MEMBASE_REG
+
+#define OP_PCOMPARE OP_ICOMPARE
+
+#endif
+
+static const IntIntrisic int_binop[] = {
+       { "op_Addition", { OP_PT_ADD, OP_PT_ADD, OP_FADD, OP_RADD } },
+       { "op_Subtraction", { OP_PT_SUB, OP_PT_SUB, OP_FSUB, OP_RSUB } },
+       { "op_Multiply", { OP_PT_MUL, OP_PT_MUL, OP_FMUL, OP_RMUL } },
+       { "op_Division", { OP_PT_DIV, OP_PT_DIV_UN, OP_FDIV, OP_RDIV } },
+       { "op_Modulus", { OP_PT_REM, OP_PT_REM_UN, OP_FREM, OP_RREM } },
+       { "op_BitwiseAnd", { OP_PT_AND, OP_PT_AND } },
+       { "op_BitwiseOr", { OP_PT_OR, OP_PT_OR } },
+       { "op_ExclusiveOr", { OP_PT_XOR, OP_PT_XOR } },
+       { "op_LeftShift", { OP_PT_SHL, OP_PT_SHL } },
+       { "op_RightShift", { OP_PT_SHR, OP_PT_SHR_UN } },
+};
+
+static const IntIntrisic int_unnop[] = {
+       { "op_UnaryPlus", { OP_MOVE, OP_MOVE, OP_FMOVE, OP_RMOVE } },
+       { "op_UnaryNegation", { OP_PT_NEG, OP_PT_NEG, OP_FNEG, OP_RNEG } },
+       { "op_OnesComplement", { OP_PT_NOT, OP_PT_NOT, OP_FNOT, OP_RNOT } },
+};
+
+static const IntIntrisic int_cmpop[] = {
+       { "op_Inequality", { OP_ICNEQ, OP_ICNEQ, OP_FCNEQ, OP_RCNEQ } },
+       { "op_Equality", { OP_ICEQ, OP_ICEQ, OP_FCEQ, OP_RCEQ } },
+       { "op_GreaterThan", { OP_ICGT, OP_ICGT_UN, OP_FCGT, OP_RCGT } },
+       { "op_GreaterThanOrEqual", { OP_ICGE, OP_ICGE_UN, OP_FCGE, OP_RCGE } },
+       { "op_LessThan", { OP_ICLT, OP_ICLT_UN, OP_FCLT, OP_RCLT } },
+       { "op_LessThanOrEqual", { OP_ICLE, OP_ICLE_UN, OP_FCLE, OP_RCLE } },
+};
+
+static const MagicTypeInfo type_info[] = {
+       //nint
+       { 0, STACK_I8, STACK_I4, STACK_PTR, OP_ICONV_TO_I8, OP_LCONV_TO_I4, OP_MOVE, OP_PT_ADD_IMM, OP_PT_SUB_IMM, OP_STORE_MEMBASE_REG, OP_PCOMPARE },
+       //nuint
+       { 1, STACK_I8, STACK_I4, STACK_PTR, OP_ICONV_TO_U8, OP_LCONV_TO_U4, OP_MOVE, OP_PT_ADD_IMM, OP_PT_SUB_IMM, OP_STORE_MEMBASE_REG, OP_PCOMPARE },
+       //nfloat
+       { 2, STACK_R8, STACK_R8, STACK_R8, OP_FCONV_TO_R8, OP_FCONV_TO_R4, OP_FMOVE, 0, 0, OP_PT_STORE_FP_MEMBASE_REG, 0 },
+};
+
+static inline gboolean mono_class_is_magic_int (MonoClass *klass);
+static inline gboolean mono_class_is_magic_float (MonoClass *klass);
+
+
+static inline gboolean
+type_size (MonoCompile *cfg, MonoType *type)
 {
-       return type;
+       if (type->type == MONO_TYPE_I4 || type->type == MONO_TYPE_U4)
+               return 4;
+       else if (type->type == MONO_TYPE_I8 || type->type == MONO_TYPE_U8)
+               return 8;
+       else if (type->type == MONO_TYPE_R4 && !type->byref && cfg->r4fp)
+               return 4;
+       else if (type->type == MONO_TYPE_R8 && !type->byref)
+               return 8;
+       return SIZEOF_VOID_P;
 }
 
+#ifndef DISABLE_JIT
+
+static gboolean is_int_type (MonoType *t);
+static gboolean is_float_type (MonoType *t);
+
+static MonoInst*
+emit_narrow (MonoCompile *cfg, const MagicTypeInfo *info, int sreg)
+{
+       MonoInst *ins;
+
+       MONO_INST_NEW (cfg, ins, info->conv_8_to_4);
+       ins->sreg1 = sreg;
+       if (info->conv_8_to_4 == OP_FCONV_TO_R4)
+               ins->type = cfg->r4_stack_type;
+       else
+               ins->type = info->small_stack_type;
+       ins->dreg = alloc_dreg (cfg, ins->type);
+       MONO_ADD_INS (cfg->cbb, ins);
+       return mono_decompose_opcode (cfg, ins);
+}
+
+static MonoInst*
+emit_widen (MonoCompile *cfg, const MagicTypeInfo *info, int sreg)
+{
+       MonoInst *ins;
+
+       if (cfg->r4fp && info->conv_4_to_8 == OP_FCONV_TO_R8)
+               MONO_INST_NEW (cfg, ins, OP_RCONV_TO_R8);
+       else
+               MONO_INST_NEW (cfg, ins, info->conv_4_to_8);
+       ins->sreg1 = sreg;
+       ins->type = info->big_stack_type;
+       ins->dreg = alloc_dreg (cfg, info->big_stack_type); 
+       MONO_ADD_INS (cfg->cbb, ins);
+       return mono_decompose_opcode (cfg, ins);
+}
+
+static MonoInst*
+emit_intrinsics (MonoCompile *cfg, MonoMethod *cmethod, MonoMethodSignature *fsig, MonoInst **args, const MagicTypeInfo *info)
+{
+       int i = 0;
+       const char *name = cmethod->name;
+       MonoInst *ins;
+       int type_index, stack_type;
+
+       if (info->op_index == 2 && cfg->r4fp && SIZEOF_VOID_P == 4) {
+               type_index = 3;
+               stack_type = STACK_R4;
+       } else {
+               type_index = info->op_index;
+               stack_type = info->stack_type;
+       }
+
+       if (!strcmp ("op_Implicit", name) || !strcmp ("op_Explicit", name)) {
+               int source_size = type_size (cfg, fsig->params [0]);
+               int dest_size = type_size (cfg, fsig->ret);
+
+               switch (info->big_stack_type) {
+               case STACK_I8:
+                       if (!is_int_type (fsig->params [0]) || !is_int_type (fsig->ret))
+                               return NULL;
+                       break;
+               case STACK_R8:
+                       if (!is_float_type (fsig->params [0]) || !is_float_type (fsig->ret))
+                               return NULL;
+                       break;
+               default:
+                       g_assert_not_reached ();
+               }
+
+               //4 -> 4 or 8 -> 8
+               if (source_size == dest_size)
+                       return args [0];
+
+               //4 -> 8
+               if (source_size < dest_size)
+                       return emit_widen (cfg, info, args [0]->dreg);
+
+               //8 -> 4
+               return emit_narrow (cfg, info, args [0]->dreg);
+       }
+
+       if (!strcmp (".ctor", name)) {
+               gboolean is_ldaddr = args [0]->opcode == OP_LDADDR;
+               int arg0 = args [1]->dreg;
+               int arg_size = type_size (cfg, fsig->params [0]);
+
+               if (arg_size > SIZEOF_VOID_P) //8 -> 4
+                       arg0 = emit_narrow (cfg, info, arg0)->dreg;
+               else if (arg_size < SIZEOF_VOID_P) //4 -> 8
+                       arg0 = emit_widen (cfg, info, arg0)->dreg;
+
+               if (is_ldaddr) { /*Eliminate LDADDR if it's initing a local var*/
+                       int dreg = ((MonoInst*)args [0]->inst_p0)->dreg;
+                       NULLIFY_INS (args [0]);
+                       EMIT_NEW_UNALU (cfg, ins, info->move, dreg, arg0);
+                       cfg->has_indirection = TRUE;
+               } else {
+                       EMIT_NEW_STORE_MEMBASE (cfg, ins, info->store_op, args [0]->dreg, 0, arg0);
+               }
+               return ins;
+       }
+
+       if (!strcmp ("op_Increment", name) || !strcmp ("op_Decrement", name)) {
+               gboolean inc = !strcmp ("op_Increment", name);
+               /* FIXME float inc is too complex to bother with*/
+               //this is broken with ints too
+               // if (!info->inc_op)
+                       return NULL;
+
+               /* We have IR for inc/dec */
+               MONO_INST_NEW (cfg, ins, inc ? info->inc_op : info->dec_op);
+               ins->dreg = alloc_dreg (cfg, info->stack_type);
+               ins->sreg1 = args [0]->dreg;
+               ins->inst_imm = 1;
+               ins->type = info->stack_type;
+               MONO_ADD_INS (cfg->cbb, ins);
+               return ins;
+       }
+
+       for (i = 0; i < sizeof (int_binop) / sizeof  (IntIntrisic); ++i) {
+               if (!strcmp (int_binop [i].op_name, name)) {
+                       if (!int_binop [i].op_table [info->op_index])
+                               return NULL;
+                       g_assert (int_binop [i].op_table [type_index]);
+
+                       MONO_INST_NEW (cfg, ins, int_binop [i].op_table [type_index]);
+                       ins->dreg = alloc_dreg (cfg, stack_type);
+                       ins->sreg1 = args [0]->dreg;
+               ins->sreg2 = args [1]->dreg;
+                       ins->type = stack_type;
+                       MONO_ADD_INS (cfg->cbb, ins);
+                       return mono_decompose_opcode (cfg, ins);
+               }
+       }
+
+       for (i = 0; i < sizeof (int_unnop) / sizeof  (IntIntrisic); ++i) {
+               if (!strcmp (int_unnop [i].op_name, name)) {
+                       g_assert (int_unnop [i].op_table [type_index]);
+
+                       MONO_INST_NEW (cfg, ins, int_unnop [i].op_table [type_index]);
+                       ins->dreg = alloc_dreg (cfg, stack_type);
+                       ins->sreg1 = args [0]->dreg;
+                       ins->type = stack_type;
+                       MONO_ADD_INS (cfg->cbb, ins);
+                       return ins;
+               }
+       }
+
+       for (i = 0; i < sizeof (int_cmpop) / sizeof  (IntIntrisic); ++i) {
+               if (!strcmp (int_cmpop [i].op_name, name)) {
+                       g_assert (int_cmpop [i].op_table [type_index]);
+
+                       if (info->compare_op) {
+                               MONO_INST_NEW (cfg, ins, info->compare_op);
+                       ins->dreg = -1;
+                               ins->sreg1 = args [0]->dreg;
+                       ins->sreg2 = args [1]->dreg;
+                               MONO_ADD_INS (cfg->cbb, ins);
+
+                               MONO_INST_NEW (cfg, ins, int_cmpop [i].op_table [type_index]);
+                       ins->dreg = alloc_preg (cfg);
+                               ins->type = STACK_I4;
+                               MONO_ADD_INS (cfg->cbb, ins);
+                       } else {
+                               MONO_INST_NEW (cfg, ins, int_cmpop [i].op_table [type_index]);
+                               ins->dreg = alloc_ireg (cfg);
+                               ins->sreg1 = args [0]->dreg;
+                       ins->sreg2 = args [1]->dreg;
+                               MONO_ADD_INS (cfg->cbb, ins);
+                       }
+
+                       return ins;
+               }
+       }
+
+       return NULL;
+}
+
+
 MonoInst*
 mono_emit_native_types_intrinsics (MonoCompile *cfg, MonoMethod *cmethod, MonoMethodSignature *fsig, MonoInst **args)
 {
+       if (mono_class_is_magic_int (cmethod->klass)) {
+               const char *class_name = cmethod->klass->name;
+               if (!strcmp ("nint", class_name))
+                       return emit_intrinsics (cfg, cmethod, fsig, args, &type_info [0]);
+               else
+                       return emit_intrinsics (cfg, cmethod, fsig, args, &type_info [1]);
+       } else if (mono_class_is_magic_float (cmethod->klass))
+               return emit_intrinsics (cfg, cmethod, fsig, args, &type_info [2]);
+
        return NULL;
 }
 
+#endif /* !DISABLE_JIT */
+
+static inline gboolean
+mono_class_is_magic_assembly (MonoClass *klass)
+{
+       if (!klass->image->assembly_name)
+               return FALSE;
+       if (!strcmp ("Xamarin.iOS", klass->image->assembly_name))
+               return TRUE;
+       if (!strcmp ("Xamarin.Mac", klass->image->assembly_name))
+               return TRUE;
+       return FALSE;
+}
+
+static inline gboolean
+mono_class_is_magic_int (MonoClass *klass)
+{
+       static MonoClass *magic_nint_class;
+       static MonoClass *magic_nuint_class;
+
+       if (klass == magic_nint_class)
+               return TRUE;
+
+       if (klass == magic_nuint_class)
+               return TRUE;
+
+       if (magic_nint_class && magic_nuint_class)
+               return FALSE;
+
+       if (!mono_class_is_magic_assembly (klass))
+               return FALSE;
+
+       if (strcmp ("System", klass->name_space) != 0)
+               return FALSE;
+
+       if (strcmp ("nint", klass->name) == 0) {
+               magic_nint_class = klass;
+               return TRUE;
+       }
+
+       if (strcmp ("nuint", klass->name) == 0){
+               magic_nuint_class = klass;
+               return TRUE;
+       }
+       return FALSE;
+}
+
+static inline gboolean
+mono_class_is_magic_float (MonoClass *klass)
+{
+       static MonoClass *magic_nfloat_class;
+
+       if (klass == magic_nfloat_class)
+               return TRUE;
+
+       if (magic_nfloat_class)
+               return FALSE;
+
+       if (!mono_class_is_magic_assembly (klass))
+               return FALSE;
+
+       if (strcmp ("System", klass->name_space) != 0)
+               return FALSE;
+
+       if (strcmp ("nfloat", klass->name) == 0) {
+               magic_nfloat_class = klass;
+               return TRUE;
+       }
+       return FALSE;
+}
+
+static gboolean
+is_int_type (MonoType *t)
+{
+       if (t->type != MONO_TYPE_I4 && t->type != MONO_TYPE_I8 && t->type != MONO_TYPE_U4 && t->type != MONO_TYPE_U8 && !mono_class_is_magic_int (mono_class_from_mono_type (t)))
+               return FALSE;
+       return TRUE;
+}
+
+static gboolean
+is_float_type (MonoType *t)
+{
+       if (t->type != MONO_TYPE_R4 && t->type != MONO_TYPE_R8 && !mono_class_is_magic_float (mono_class_from_mono_type (t)))
+               return FALSE;
+       return TRUE;
+}
+
+MonoType*
+mini_native_type_replace_type (MonoType *type)
+{
+       MonoClass *klass;
+
+       if (type->type != MONO_TYPE_VALUETYPE)
+               return type;
+       klass = type->data.klass;
+
+       if (mono_class_is_magic_int (klass))
+               return type->byref ? &mono_defaults.int_class->this_arg : &mono_defaults.int_class->byval_arg;
+       if (mono_class_is_magic_float (klass))
+#if SIZEOF_VOID_P == 8
+               return type->byref ? &mono_defaults.double_class->this_arg : &mono_defaults.double_class->byval_arg;
+#else
+               return type->byref ? &mono_defaults.single_class->this_arg : &mono_defaults.single_class->byval_arg;
 #endif
+       return type;
+}
index 7e1e72ce4978c9c82fcefbe77a3da12fc52102d4..ad48c07158e3f0877ae4033b5c2dd0ab9a1f207a 100644 (file)
@@ -2,6 +2,7 @@
  * Copyright 2003 Ximian, Inc
  * Copyright 2003-2011 Novell Inc
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 MINI_OP(OP_LOAD,       "load", NONE, NONE, NONE)
 MINI_OP(OP_LDADDR,     "ldaddr", IREG, NONE, NONE)
index 63198d79083cdafc1718a111016e0be15ad63a87..95b45b56afb55485e6fef0845395d5e4638f6177 100644 (file)
@@ -9,6 +9,7 @@
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
  *
  * See LICENSE for licensing information.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <signal.h>
@@ -26,7 +27,7 @@
 #include <sys/syscall.h>
 #endif
 #include <errno.h>
-
+#include <sched.h>
 
 #include <mono/metadata/assembly.h>
 #include <mono/metadata/loader.h>
@@ -58,6 +59,7 @@
 #include <mono/utils/dtrace.h>
 #include <mono/utils/mono-signal-handler.h>
 #include <mono/utils/mono-threads.h>
+#include <mono/utils/mono-threads-posix-signals.h>
 
 #include "mini.h"
 #include <string.h>
 
 #include "jit-icalls.h"
 
+#ifdef PLATFORM_MACOSX
+#include <mach/mach.h>
+#include <mach/mach_time.h>
+#include <mach/clock.h>
+#endif
+
 #if defined(__native_client__) || defined(HOST_WATCHOS)
 
 void
@@ -234,21 +242,11 @@ MONO_SIG_HANDLER_FUNC (static, sigabrt_signal_handler)
 #define FULL_STAT_PROFILER_BACKTRACE 0
 #endif
 
-#ifdef SIGPROF
-
-static int profiling_signal_in_use;
-
-#if defined(__ia64__) || defined(__sparc__) || defined(sparc)
-
-MONO_SIG_HANDLER_FUNC (static, sigprof_signal_handler)
-{
-       if (mono_chain_signal (MONO_SIG_HANDLER_PARAMS))
-               return;
-
-       NOT_IMPLEMENTED;
-}
+#if (defined (USE_POSIX_BACKEND) && defined (SIGRTMIN)) || defined (SIGPROF)
+#define HAVE_PROFILER_SIGNAL
+#endif
 
-#else
+#ifdef HAVE_PROFILER_SIGNAL
 
 static void
 per_thread_profiler_hit (void *ctx)
@@ -324,31 +322,42 @@ per_thread_profiler_hit (void *ctx)
        }
 }
 
-MONO_SIG_HANDLER_FUNC (static, sigprof_signal_handler)
+static MonoNativeThreadId sampling_thread;
+
+static gint32 profiler_signals_sent;
+static gint32 profiler_signals_received;
+static gint32 profiler_signals_accepted;
+static gint32 profiler_interrupt_signals_received;
+
+MONO_SIG_HANDLER_FUNC (static, profiler_signal_handler)
 {
        int old_errno = errno;
        int hp_save_index;
        MONO_SIG_HANDLER_GET_CONTEXT;
 
+       /* See the comment in mono_runtime_shutdown_stat_profiler (). */
+       if (mono_native_thread_id_get () == sampling_thread) {
+#ifdef HAVE_CLOCK_NANOSLEEP
+               if (mono_profiler_get_sampling_mode () == MONO_PROFILER_STAT_MODE_PROCESS) {
+                       InterlockedIncrement (&profiler_interrupt_signals_received);
+                       return;
+               }
+#endif
+
+               g_error ("%s: Unexpected profiler signal received by the sampler thread", __func__);
+       }
+
+       InterlockedIncrement (&profiler_signals_received);
+
        if (mono_thread_info_get_small_id () == -1)
                return; //an non-attached thread got the signal
 
        if (!mono_domain_get () || !mono_native_tls_get_value (mono_jit_tls_id))
                return; //thread in the process of dettaching
 
-       hp_save_index = mono_hazard_pointer_save_for_signal_handler ();
-
-       /* If we can't consume a profiling request it means we're the initiator. */
-       if (!(mono_threads_consume_async_jobs () & MONO_SERVICE_REQUEST_SAMPLE)) {
-               FOREACH_THREAD_SAFE (info) {
-                       if (mono_thread_info_get_tid (info) == mono_native_thread_id_get () ||
-                           !mono_thread_info_is_live (info))
-                               continue;
+       InterlockedIncrement (&profiler_signals_accepted);
 
-                       mono_threads_add_async_job (info, MONO_SERVICE_REQUEST_SAMPLE);
-                       mono_threads_pthread_kill (info, profiling_signal_in_use);
-               } FOREACH_THREAD_SAFE_END
-       }
+       hp_save_index = mono_hazard_pointer_save_for_signal_handler ();
 
        mono_thread_info_set_is_async_context (TRUE);
        per_thread_profiler_hit (ctx);
@@ -360,7 +369,6 @@ MONO_SIG_HANDLER_FUNC (static, sigprof_signal_handler)
        mono_chain_signal (MONO_SIG_HANDLER_PARAMS);
 }
 
-#endif
 #endif
 
 MONO_SIG_HANDLER_FUNC (static, sigquit_signal_handler)
@@ -521,123 +529,334 @@ mono_runtime_cleanup_handlers (void)
        free_saved_signal_handlers ();
 }
 
-#ifdef HAVE_LINUX_RTC_H
-#include <linux/rtc.h>
-#include <sys/ioctl.h>
-#include <fcntl.h>
-static int rtc_fd = -1;
+#ifdef HAVE_PROFILER_SIGNAL
 
-static int
-enable_rtc_timer (gboolean enable)
+static volatile gint32 sampling_thread_running;
+
+#ifdef PLATFORM_MACOSX
+
+static clock_serv_t sampling_clock_service;
+
+static void
+clock_init (void)
 {
-       int flags;
-       flags = fcntl (rtc_fd, F_GETFL);
-       if (flags < 0) {
-               perror ("getflags");
-               return 0;
-       }
-       if (enable)
-               flags |= FASYNC;
-       else
-               flags &= ~FASYNC;
-       if (fcntl (rtc_fd, F_SETFL, flags) == -1) {
-               perror ("setflags");
-               return 0;
-       }
-       return 1;
+       kern_return_t ret;
+
+       do {
+               ret = host_get_clock_service (mach_host_self (), SYSTEM_CLOCK, &sampling_clock_service);
+       } while (ret == KERN_ABORTED);
+
+       if (ret != KERN_SUCCESS)
+               g_error ("%s: host_get_clock_service () returned %d", __func__, ret);
 }
-#endif
 
-void
-mono_runtime_shutdown_stat_profiler (void)
+static void
+clock_cleanup (void)
 {
-#ifdef HAVE_LINUX_RTC_H
-       if (rtc_fd >= 0)
-               enable_rtc_timer (FALSE);
-#endif
+       kern_return_t ret;
+
+       do {
+               ret = mach_port_deallocate (mach_task_self (), sampling_clock_service);
+       } while (ret == KERN_ABORTED);
+
+       if (ret != KERN_SUCCESS)
+               g_error ("%s: mach_port_deallocate () returned %d", __func__, ret);
 }
 
-#ifdef ITIMER_PROF
-static int
-get_itimer_mode (void)
+static guint64
+clock_get_time_ns (void)
 {
-       switch (mono_profiler_get_sampling_mode ()) {
-       case MONO_PROFILER_STAT_MODE_PROCESS: return ITIMER_PROF;
-       case MONO_PROFILER_STAT_MODE_REAL: return ITIMER_REAL;
-       }
-       g_assert_not_reached ();
-       return 0;
+       kern_return_t ret;
+       mach_timespec_t mach_ts;
+
+       do {
+               ret = clock_get_time (sampling_clock_service, &mach_ts);
+       } while (ret == KERN_ABORTED);
+
+       if (ret != KERN_SUCCESS)
+               g_error ("%s: clock_get_time () returned %d", __func__, ret);
+
+       return ((guint64) mach_ts.tv_sec * 1000000000) + (guint64) mach_ts.tv_nsec;
+}
+
+static void
+clock_sleep_ns_abs (guint64 ns_abs)
+{
+       kern_return_t ret;
+       mach_timespec_t then, remain_unused;
+
+       then.tv_sec = ns_abs / 1000000000;
+       then.tv_nsec = ns_abs % 1000000000;
+
+       do {
+               ret = clock_sleep (sampling_clock_service, TIME_ABSOLUTE, then, &remain_unused);
+
+               if (ret != KERN_SUCCESS && ret != KERN_ABORTED)
+                       g_error ("%s: clock_sleep () returned %d", __func__, ret);
+       } while (ret == KERN_ABORTED && InterlockedRead (&sampling_thread_running));
 }
 
-static int
-get_itimer_signal (void)
+#else
+
+clockid_t sampling_posix_clock;
+
+static void
+clock_init (void)
 {
        switch (mono_profiler_get_sampling_mode ()) {
-       case MONO_PROFILER_STAT_MODE_PROCESS: return SIGPROF;
-       case MONO_PROFILER_STAT_MODE_REAL: return SIGALRM;
+       case MONO_PROFILER_STAT_MODE_PROCESS:
+#ifdef HAVE_CLOCK_NANOSLEEP
+               /*
+                * If we don't have clock_nanosleep (), measuring the process time
+                * makes very little sense as we can only use nanosleep () to sleep on
+                * real time.
+                */
+               sampling_posix_clock = CLOCK_PROCESS_CPUTIME_ID;
+               break;
+#endif
+       case MONO_PROFILER_STAT_MODE_REAL: sampling_posix_clock = CLOCK_MONOTONIC; break;
+       default: g_assert_not_reached (); break;
        }
-       g_assert_not_reached ();
-       return 0;
 }
+
+static void
+clock_cleanup (void)
+{
+}
+
+static guint64
+clock_get_time_ns (void)
+{
+       struct timespec ts;
+
+       if (clock_gettime (sampling_posix_clock, &ts) == -1)
+               g_error ("%s: clock_gettime () returned -1, errno = %d", __func__, errno);
+
+       return ((guint64) ts.tv_sec * 1000000000) + (guint64) ts.tv_nsec;
+}
+
+static void
+clock_sleep_ns_abs (guint64 ns_abs)
+{
+#ifdef HAVE_CLOCK_NANOSLEEP
+       int ret;
+       struct timespec then;
+
+       then.tv_sec = ns_abs / 1000000000;
+       then.tv_nsec = ns_abs % 1000000000;
+
+       do {
+               ret = clock_nanosleep (sampling_posix_clock, TIMER_ABSTIME, &then, NULL);
+
+               if (ret != 0 && ret != EINTR)
+                       g_error ("%s: clock_nanosleep () returned %d", __func__, ret);
+       } while (ret == EINTR && InterlockedRead (&sampling_thread_running));
+#else
+       int ret;
+       gint64 diff;
+       struct timespec req;
+
+       /*
+        * What follows is a crude attempt at emulating clock_nanosleep () on OSs
+        * which don't provide it (e.g. FreeBSD).
+        *
+        * The problem with nanosleep () is that if it is interrupted by a signal,
+        * time will drift as a result of having to restart the call after the
+        * signal handler has finished. For this reason, we avoid using the rem
+        * argument of nanosleep (). Instead, before every nanosleep () call, we
+        * check if enough time has passed to satisfy the sleep request. If yes, we
+        * simply return. If not, we calculate the difference and do another sleep.
+        *
+        * This should reduce the amount of drift that happens because we account
+        * for the time spent executing the signal handler, which nanosleep () is
+        * not guaranteed to do for the rem argument.
+        *
+        * The downside to this approach is that it is slightly expensive: We have
+        * to make an extra system call to retrieve the current time whenever we're
+        * going to restart a nanosleep () call. This is unlikely to be a problem
+        * in practice since the sampling thread won't be receiving many signals in
+        * the first place (it's a tools thread, so no STW), and because typical
+        * sleep periods for the thread are many orders of magnitude bigger than
+        * the time it takes to actually perform that system call (just a few
+        * nanoseconds).
+        */
+       do {
+               diff = (gint64) ns_abs - (gint64) clock_get_time_ns ();
+
+               if (diff <= 0)
+                       break;
+
+               req.tv_sec = diff / 1000000000;
+               req.tv_nsec = diff % 1000000000;
+
+               if ((ret = nanosleep (&req, NULL)) == -1 && errno != EINTR)
+                       g_error ("%s: nanosleep () returned -1, errno = %d", __func__, errno);
+       } while (ret == -1 && InterlockedRead (&sampling_thread_running));
 #endif
+}
+
+#endif
+
+static int profiler_signal;
+static volatile gint32 sampling_thread_exiting;
+
+static mono_native_thread_return_t
+sampling_thread_func (void *data)
+{
+       mono_threads_attach_tools_thread ();
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Profiler sampler");
+
+       gint64 rate = 1000000000 / mono_profiler_get_sampling_rate ();
+
+       int old_policy;
+       struct sched_param old_sched;
+       pthread_getschedparam (pthread_self (), &old_policy, &old_sched);
+
+       /*
+        * Attempt to switch the thread to real time scheduling. This will not
+        * necessarily work on all OSs; for example, most Linux systems will give
+        * us EPERM here unless configured to allow this.
+        *
+        * TODO: This does not work on Mac (and maybe some other OSs). On Mac, we
+        * have to use the Mach thread policy routines to switch to real-time
+        * scheduling. This is quite tricky as we need to specify how often we'll
+        * be doing work (easy), the normal processing time needed (also easy),
+        * and the maximum amount of processing time needed (hard). This is
+        * further complicated by the fact that if we misbehave and take too long
+        * to do our work, the kernel may knock us back down to the normal thread
+        * scheduling policy without telling us.
+        */
+       struct sched_param sched = { .sched_priority = sched_get_priority_max (SCHED_FIFO) };
+       pthread_setschedparam (pthread_self (), SCHED_FIFO, &sched);
+
+       clock_init ();
+
+       guint64 sleep = clock_get_time_ns ();
+
+       while (InterlockedRead (&sampling_thread_running)) {
+               sleep += rate;
+
+               FOREACH_THREAD_SAFE (info) {
+                       /* info should never be this thread as we're a tools thread. */
+                       g_assert (mono_thread_info_get_tid (info) != mono_native_thread_id_get ());
+
+                       mono_threads_pthread_kill (info, profiler_signal);
+                       InterlockedIncrement (&profiler_signals_sent);
+               } FOREACH_THREAD_SAFE_END
+
+               clock_sleep_ns_abs (sleep);
+       }
+
+       InterlockedWrite (&sampling_thread_exiting, 1);
+
+       clock_cleanup ();
+
+       pthread_setschedparam (pthread_self (), old_policy, &old_sched);
+
+       mono_thread_info_detach ();
+
+       return NULL;
+}
 
 void
-mono_runtime_setup_stat_profiler (void)
+mono_runtime_shutdown_stat_profiler (void)
 {
-#ifdef ITIMER_PROF
-       struct itimerval itval;
-       static int inited = 0;
-#ifdef HAVE_LINUX_RTC_H
-       const char *rtc_freq;
-       if (!inited && (rtc_freq = g_getenv ("MONO_RTC"))) {
-               int freq = 0;
-               inited = 1;
-               if (*rtc_freq)
-                       freq = atoi (rtc_freq);
-               if (!freq)
-                       freq = 1024;
-               rtc_fd = open ("/dev/rtc", O_RDONLY);
-               if (rtc_fd == -1) {
-                       perror ("open /dev/rtc");
-                       return;
-               }
-               profiling_signal_in_use = SIGPROF;
-               add_signal_handler (profiling_signal_in_use, sigprof_signal_handler, SA_RESTART);
-               if (ioctl (rtc_fd, RTC_IRQP_SET, freq) == -1) {
-                       perror ("set rtc freq");
-                       return;
-               }
-               if (ioctl (rtc_fd, RTC_PIE_ON, 0) == -1) {
-                       perror ("start rtc");
-                       return;
-               }
-               if (fcntl (rtc_fd, F_SETSIG, SIGPROF) == -1) {
-                       perror ("setsig");
-                       return;
-               }
-               if (fcntl (rtc_fd, F_SETOWN, getpid ()) == -1) {
-                       perror ("setown");
-                       return;
+       InterlockedWrite (&sampling_thread_running, 0);
+
+#ifdef HAVE_CLOCK_NANOSLEEP
+       /*
+        * There is a slight problem when we're using CLOCK_PROCESS_CPUTIME_ID: If
+        * we're shutting down and there's largely no activity in the process other
+        * than waiting for the sampler thread to shut down, it can take upwards of
+        * 20 seconds (depending on a lot of factors) for us to shut down because
+        * the sleep progresses very slowly as a result of the low CPU activity.
+        *
+        * We fix this by repeatedly sending the profiler signal to the sampler
+        * thread in order to interrupt the sleep. clock_sleep_ns_abs () will check
+        * sampling_thread_running upon an interrupt and return immediately if it's
+        * zero. profiler_signal_handler () has a special case to ignore the signal
+        * for the sampler thread.
+        *
+        * We do not need to do this on platforms where we use a regular sleep
+        * based on a monotonic clock. The sleep will return in a reasonable amount
+        * of time in those cases.
+        */
+       if (mono_profiler_get_sampling_mode () == MONO_PROFILER_STAT_MODE_PROCESS) {
+               MonoThreadInfo *info;
+
+               // Did it shut down already?
+               if ((info = mono_thread_info_lookup (sampling_thread))) {
+                       while (!InterlockedRead (&sampling_thread_exiting)) {
+                               mono_threads_pthread_kill (info, profiler_signal);
+                               mono_thread_info_usleep (10 * 1000 /* 10ms */);
+                       }
+
+                       // Make sure info can be freed.
+                       mono_hazard_pointer_clear (mono_hazard_pointer_get (), 1);
                }
-               enable_rtc_timer (TRUE);
-               return;
        }
-       if (rtc_fd >= 0)
-               return;
 #endif
 
-       itval.it_interval.tv_usec = (1000000 / mono_profiler_get_sampling_rate ()) - 1;
-       itval.it_interval.tv_sec = 0;
-       itval.it_value = itval.it_interval;
-       if (inited)
-               return;
-       inited = 1;
-       profiling_signal_in_use = get_itimer_signal ();
-       add_signal_handler (profiling_signal_in_use, sigprof_signal_handler, SA_RESTART);
-       setitimer (get_itimer_mode (), &itval, NULL);
+       pthread_join (sampling_thread, NULL);
+
+       /*
+        * We can't safely remove the signal handler because we have no guarantee
+        * that all pending signals have been delivered at this point. This should
+        * not really be a problem anyway.
+        */
+       //remove_signal_handler (profiler_signal);
+}
+
+void
+mono_runtime_setup_stat_profiler (void)
+{
+       /*
+        * Use a real-time signal when possible. This gives us roughly a 99% signal
+        * delivery rate in all cases. On the other hand, using a regular signal
+        * tends to result in awful delivery rates when the application is heavily
+        * loaded.
+        *
+        * We avoid real-time signals on Android as they're super broken in certain
+        * API levels (too small sigset_t, nonsensical SIGRTMIN/SIGRTMAX values,
+        * etc).
+        *
+        * TODO: On Mac, we should explore using the Mach thread suspend/resume
+        * functions and doing the stack walk from the sampling thread. This would
+        * get us a 100% sampling rate. However, this may interfere with the GC's
+        * STW logic. Could perhaps be solved by taking the suspend lock.
+        */
+#if defined (USE_POSIX_BACKEND) && defined (SIGRTMIN) && !defined (PLATFORM_ANDROID)
+       /* Just take the first real-time signal we can get. */
+       profiler_signal = mono_threads_posix_signal_search_alternative (-1);
+#else
+       profiler_signal = SIGPROF;
 #endif
+
+       add_signal_handler (profiler_signal, profiler_signal_handler, SA_RESTART);
+
+       mono_counters_register ("Sampling signals sent", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &profiler_signals_sent);
+       mono_counters_register ("Sampling signals received", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &profiler_signals_received);
+       mono_counters_register ("Sampling signals accepted", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &profiler_signals_accepted);
+       mono_counters_register ("Shutdown signals received", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &profiler_interrupt_signals_received);
+
+       InterlockedWrite (&sampling_thread_running, 1);
+       mono_native_thread_create (&sampling_thread, sampling_thread_func, NULL);
+}
+
+#else
+
+void
+mono_runtime_shutdown_stat_profiler (void)
+{
 }
 
+void
+mono_runtime_setup_stat_profiler (void)
+{
+}
+
+#endif
+
 #if !defined(PLATFORM_MACOSX)
 pid_t
 mono_runtime_syscall_fork ()
index cce368bdcffebb3489011cd609228d17131ab67e..2c0750bfc72ca13e24597e8a2c98fcadcb0f58cd 100644 (file)
@@ -1,3 +1,4 @@
+
 /*
  * mini-runtime.c: Runtime code for the JIT
  *
@@ -8,6 +9,7 @@
  * Copyright 2002-2003 Ximian, Inc.
  * Copyright 2003-2010 Novell, Inc.
  * Copyright 2011-2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -1110,8 +1112,6 @@ mono_thread_attach_cb (intptr_t tid, gpointer stack_start)
        thread = mono_thread_info_current_unchecked ();
        if (thread)
                thread->jit_data = jit_tls;
-       if (mono_profiler_get_events () & MONO_PROFILE_STATISTICAL)
-               mono_runtime_setup_stat_profiler ();
 
        mono_arch_cpu_init ();
 }
@@ -2390,7 +2390,7 @@ create_runtime_invoke_info (MonoDomain *domain, MonoMethod *method, gpointer com
 
        if (!info->dyn_call_info) {
                if (mono_llvm_only) {
-#ifndef ENABLE_GSHAREDVT
+#ifndef MONO_ARCH_GSHAREDVT_SUPPORTED
                        g_assert_not_reached ();
 #endif
                        info->gsharedvt_invoke = TRUE;
@@ -2502,7 +2502,7 @@ mono_llvmonly_runtime_invoke (MonoMethod *method, RuntimeInvokeInfo *info, void
                mono_error_set_exception_instance (error, (MonoException*) *exc);
 
        if (sig->ret->type != MONO_TYPE_VOID && info->ret_box_class)
-               return mono_value_box (domain, info->ret_box_class, retval);
+               return mono_value_box_checked (domain, info->ret_box_class, retval, error);
        else
                return *(MonoObject**)retval;
 }
@@ -2677,7 +2677,7 @@ mono_jit_runtime_invoke (MonoMethod *method, void *obj, void **params, MonoObjec
                mono_arch_finish_dyn_call (info->dyn_call_info, buf);
 
                if (info->ret_box_class)
-                       return mono_value_box (domain, info->ret_box_class, retval);
+                       return mono_value_box_checked (domain, info->ret_box_class, retval, error);
                else
                        return *(MonoObject**)retval;
        }
@@ -3063,13 +3063,13 @@ mono_jit_create_remoting_trampoline (MonoDomain *domain, MonoMethod *method, Mon
 }
 #endif
 
-static void
+static G_GNUC_UNUSED void
 no_imt_trampoline (void)
 {
        g_assert_not_reached ();
 }
 
-static void
+static G_GNUC_UNUSED void
 no_vcall_trampoline (void)
 {
        g_assert_not_reached ();
@@ -3395,7 +3395,7 @@ register_jit_stats (void)
        mono_counters_register ("Methods from AOT", MONO_COUNTER_JIT | MONO_COUNTER_INT, &mono_jit_stats.methods_aot);
        mono_counters_register ("Methods JITted using mono JIT", MONO_COUNTER_JIT | MONO_COUNTER_INT, &mono_jit_stats.methods_without_llvm);
        mono_counters_register ("Methods JITted using LLVM", MONO_COUNTER_JIT | MONO_COUNTER_INT, &mono_jit_stats.methods_with_llvm);
-       mono_counters_register ("JIT/method-to-IR (sec)", MONO_COUNTER_JIT | MONO_COUNTER_DOUBLE, &mono_jit_stats.jit_method_to_ir);
+       mono_counters_register ("JIT/method_to_ir (sec)", MONO_COUNTER_JIT | MONO_COUNTER_DOUBLE, &mono_jit_stats.jit_method_to_ir);
        mono_counters_register ("JIT/liveness_handle_exception_clauses (sec)", MONO_COUNTER_JIT | MONO_COUNTER_DOUBLE, &mono_jit_stats.jit_liveness_handle_exception_clauses);
        mono_counters_register ("JIT/handle_out_of_line_bblock (sec)", MONO_COUNTER_JIT | MONO_COUNTER_DOUBLE, &mono_jit_stats.jit_handle_out_of_line_bblock);
        mono_counters_register ("JIT/decompose_long_opts (sec)", MONO_COUNTER_JIT | MONO_COUNTER_DOUBLE, &mono_jit_stats.jit_decompose_long_opts);
@@ -3838,6 +3838,9 @@ mini_init (const char *filename, const char *runtime_version)
        mono_thread_attach (domain);
 #endif
 
+       if (mono_profiler_get_events () & MONO_PROFILE_STATISTICAL)
+               mono_runtime_setup_stat_profiler ();
+
        mono_profiler_runtime_initialized ();
 
        MONO_VES_INIT_END ();
@@ -3898,8 +3901,8 @@ register_icalls (void)
        register_icall (mono_thread_interruption_checkpoint, "mono_thread_interruption_checkpoint", "object", FALSE);
        register_icall (mono_thread_force_interruption_checkpoint_noraise, "mono_thread_force_interruption_checkpoint_noraise", "object", FALSE);
 #ifndef DISABLE_REMOTING
-       register_icall (mono_load_remote_field_new, "mono_load_remote_field_new", "object object ptr ptr", FALSE);
-       register_icall (mono_store_remote_field_new, "mono_store_remote_field_new", "void object ptr ptr object", FALSE);
+       register_icall (mono_load_remote_field_new_icall, "mono_load_remote_field_new_icall", "object object ptr ptr", FALSE);
+       register_icall (mono_store_remote_field_new_icall, "mono_store_remote_field_new_icall", "void object ptr ptr object", FALSE);
 #endif
 
 #if defined(__native_client__) || defined(__native_client_codegen__)
@@ -4048,7 +4051,7 @@ register_icalls (void)
        register_icall (mono_helper_stelem_ref_check, "mono_helper_stelem_ref_check", "void object object", FALSE);
        register_icall (ves_icall_object_new, "ves_icall_object_new", "object ptr ptr", FALSE);
        register_icall (ves_icall_object_new_specific, "ves_icall_object_new_specific", "object ptr", FALSE);
-       register_icall (mono_array_new, "mono_array_new", "object ptr ptr int32", FALSE);
+       register_icall (ves_icall_array_new, "ves_icall_array_new", "object ptr ptr int32", FALSE);
        register_icall (ves_icall_array_new_specific, "ves_icall_array_new_specific", "object ptr int32", FALSE);
        register_icall (ves_icall_runtime_class_init, "ves_icall_runtime_class_init", "void ptr", FALSE);
        register_icall (mono_ldftn, "mono_ldftn", "ptr ptr", FALSE);
@@ -4162,7 +4165,8 @@ print_jit_stats (void)
 void
 mini_cleanup (MonoDomain *domain)
 {
-       mono_runtime_shutdown_stat_profiler ();
+       if (mono_profiler_get_events () & MONO_PROFILE_STATISTICAL)
+               mono_runtime_shutdown_stat_profiler ();
 
 #ifndef DISABLE_COM
        cominterop_release_all_rcws ();
@@ -4179,12 +4183,12 @@ mini_cleanup (MonoDomain *domain)
        /* This accesses metadata so needs to be called before runtime shutdown */
        print_jit_stats ();
 
-       mono_profiler_shutdown ();
-
 #ifndef MONO_CROSS_COMPILE
        mono_runtime_cleanup (domain);
 #endif
 
+       mono_profiler_shutdown ();
+
        free_jit_tls_data ((MonoJitTlsData *)mono_native_tls_get_value (mono_jit_tls_id));
 
        mono_icall_cleanup ();
index ed844636c525ed7b50cf746cfca057e22f5c301f..c464a0033a77c727829ba44f5e6acea3bba0e84c 100644 (file)
@@ -2,6 +2,7 @@
  * (C) 2003 Ximian, Inc.
  * (C) 2003-2011 Novell, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <glib.h>
@@ -1057,36 +1058,6 @@ mono_rgctx_lazy_fetch_trampoline (mgreg_t *regs, guint8 *code, gpointer data, gu
        return res;
 }
 
-/*
- * Precompute data to speed up mono_delegate_trampoline ().
- * METHOD might be NULL.
- */
-static MonoDelegateTrampInfo*
-create_delegate_trampoline_data (MonoDomain *domain, MonoClass *klass, MonoMethod *method)
-{
-       MonoDelegateTrampInfo *tramp_data;
-       MonoMethod *invoke;
-       MonoError err;
-
-       // Precompute the delegate invoke impl and pass it to the delegate trampoline
-       invoke = mono_get_delegate_invoke (klass);
-       g_assert (invoke);
-
-       tramp_data = (MonoDelegateTrampInfo *)mono_domain_alloc0 (domain, sizeof (MonoDelegateTrampInfo));
-       tramp_data->invoke = invoke;
-       tramp_data->invoke_sig = mono_method_signature (invoke);
-       tramp_data->impl_this = mono_arch_get_delegate_invoke_impl (mono_method_signature (invoke), TRUE);
-       tramp_data->impl_nothis = mono_arch_get_delegate_invoke_impl (mono_method_signature (invoke), FALSE);
-       tramp_data->method = method;
-       if (method) {
-               mono_error_init (&err);
-               tramp_data->sig = mono_method_signature_checked (method, &err);
-               tramp_data->need_rgctx_tramp = mono_method_needs_static_rgctx_invoke (method, FALSE);
-       }
-
-       return tramp_data;
-}
-
 /**
  * mono_delegate_trampoline:
  *
@@ -1576,11 +1547,13 @@ mono_create_jit_trampoline_from_token (MonoImage *image, guint32 token)
 /*
  * mono_create_delegate_trampoline_info:
  *
- *   Create a delegate trampoline for the KLASS+METHOD pair.
+ *  Create a trampoline info structure for the KLASS+METHOD pair.
  */
 MonoDelegateTrampInfo*
 mono_create_delegate_trampoline_info (MonoDomain *domain, MonoClass *klass, MonoMethod *method)
 {
+       MonoMethod *invoke;
+       MonoError error;
        MonoDelegateTrampInfo *tramp_info;
        MonoClassMethodPair pair, *dpair;
        guint32 code_size = 0;
@@ -1593,8 +1566,20 @@ mono_create_delegate_trampoline_info (MonoDomain *domain, MonoClass *klass, Mono
        if (tramp_info)
                return tramp_info;
 
-       tramp_info = create_delegate_trampoline_data (domain, klass, method);
+       invoke = mono_get_delegate_invoke (klass);
+       g_assert (invoke);
 
+       tramp_info = (MonoDelegateTrampInfo *)mono_domain_alloc0 (domain, sizeof (MonoDelegateTrampInfo));
+       tramp_info->invoke = invoke;
+       tramp_info->invoke_sig = mono_method_signature (invoke);
+       tramp_info->impl_this = mono_arch_get_delegate_invoke_impl (mono_method_signature (invoke), TRUE);
+       tramp_info->impl_nothis = mono_arch_get_delegate_invoke_impl (mono_method_signature (invoke), FALSE);
+       tramp_info->method = method;
+       if (method) {
+               mono_error_init (&error);
+               tramp_info->sig = mono_method_signature_checked (method, &error);
+               tramp_info->need_rgctx_tramp = mono_method_needs_static_rgctx_invoke (method, FALSE);
+       }
        tramp_info->invoke_impl = mono_create_specific_trampoline (tramp_info, MONO_TRAMPOLINE_DELEGATE, domain, &code_size);
        g_assert (code_size);
 
index 4bcc19b5bfb64d86d12da04f3653159639057a1f..621a7a5fc31970e22d3e75e4993623ae10dddece 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2003-2008 Ximian, Inc.
  *
  * See LICENSE for licensing information.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <signal.h>
@@ -58,12 +59,14 @@ void
 mono_runtime_install_handlers (void)
 {
 #ifndef MONO_CROSS_COMPILE
-       win32_seh_init();
-       win32_seh_set_handler(SIGFPE, mono_sigfpe_signal_handler);
-       win32_seh_set_handler(SIGILL, mono_sigill_signal_handler);
-       win32_seh_set_handler(SIGSEGV, mono_sigsegv_signal_handler);
-       if (mini_get_debug_options ()->handle_sigint)
-               win32_seh_set_handler(SIGINT, mono_sigint_signal_handler);
+       if (!mono_aot_only) {
+               win32_seh_init();
+               win32_seh_set_handler(SIGFPE, mono_sigfpe_signal_handler);
+               win32_seh_set_handler(SIGILL, mono_sigill_signal_handler);
+               win32_seh_set_handler(SIGSEGV, mono_sigsegv_signal_handler);
+               if (mini_get_debug_options ()->handle_sigint)
+                       win32_seh_set_handler(SIGINT, mono_sigint_signal_handler);
+       }
 #endif
 }
 
@@ -71,7 +74,9 @@ void
 mono_runtime_cleanup_handlers (void)
 {
 #ifndef MONO_CROSS_COMPILE
-       win32_seh_cleanup();
+       if (!mono_aot_only) {
+               win32_seh_cleanup();
+       }
 #endif
 }
 
diff --git a/mono/mini/mini-x86-gsharedvt.c b/mono/mini/mini-x86-gsharedvt.c
new file mode 100644 (file)
index 0000000..130d48e
--- /dev/null
@@ -0,0 +1,210 @@
+/*
+ * mini-x86-gsharedvt.c: gsharedvt support code for x86
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include "mini.h"
+
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+/*
+ * GSHAREDVT
+ */
+
+gboolean
+mono_arch_gsharedvt_sig_supported (MonoMethodSignature *sig)
+{
+       /*
+       if (sig->ret && is_variable_size (sig->ret))
+               return FALSE;
+       */
+       return TRUE;
+}
+
+/*
+ * mono_arch_get_gsharedvt_call_info:
+ *
+ *   Compute calling convention information for marshalling a call between NORMAL_SIG and GSHAREDVT_SIG.
+ * If GSHAREDVT_IN is TRUE, then the caller calls using the signature NORMAL_SIG but the call is received by
+ * a method with signature GSHAREDVT_SIG, otherwise its the other way around.
+ */
+gpointer
+mono_arch_get_gsharedvt_call_info (gpointer addr, MonoMethodSignature *normal_sig, MonoMethodSignature *gsharedvt_sig, gboolean gsharedvt_in, gint32 vcall_offset, gboolean calli)
+{
+       GSharedVtCallInfo *info;
+       CallInfo *caller_cinfo, *callee_cinfo;
+       MonoMethodSignature *caller_sig, *callee_sig;
+       int i, j;
+       gboolean var_ret = FALSE;
+       CallInfo *cinfo, *gcinfo;
+       MonoMethodSignature *sig, *gsig;
+       GPtrArray *map;
+
+       if (gsharedvt_in) {
+               caller_sig = normal_sig;
+               callee_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+       } else {
+               callee_sig = normal_sig;
+               callee_cinfo = mono_arch_get_call_info (NULL, callee_sig);
+               caller_sig = gsharedvt_sig;
+               caller_cinfo = mono_arch_get_call_info (NULL, caller_sig);
+       }
+
+       /*
+        * If GSHAREDVT_IN is true, this means we are transitioning from normal to gsharedvt code. The caller uses the
+        * normal call signature, while the callee uses the gsharedvt signature.
+        * If GSHAREDVT_IN is false, its the other way around.
+        */
+
+       /* sig/cinfo describes the normal call, while gsig/gcinfo describes the gsharedvt call */
+       if (gsharedvt_in) {
+               sig = caller_sig;
+               gsig = callee_sig;
+               cinfo = caller_cinfo;
+               gcinfo = callee_cinfo;
+       } else {
+               sig = callee_sig;
+               gsig = caller_sig;
+               cinfo = callee_cinfo;
+               gcinfo = caller_cinfo;
+       }
+
+       if (gcinfo->vtype_retaddr && gsig->ret && mini_is_gsharedvt_type (gsig->ret)) {
+               /*
+                * The return type is gsharedvt
+                */
+               var_ret = TRUE;
+       }
+
+       /*
+        * The stack looks like this:
+        * <arguments>
+        * <ret addr>
+        * <saved ebp>
+        * <call area>
+        * We have to map the stack slots in <arguments> to the stack slots in <call area>.
+        */
+       map = g_ptr_array_new ();
+
+       if (cinfo->vtype_retaddr) {
+               /*
+                * Map ret arg.
+                * This handles the case when the method returns a normal vtype, and when it returns a type arg, and its instantiated
+                * with a vtype.
+                */             
+               g_ptr_array_add (map, GUINT_TO_POINTER (caller_cinfo->vret_arg_offset / sizeof (gpointer)));
+               g_ptr_array_add (map, GUINT_TO_POINTER (callee_cinfo->vret_arg_offset / sizeof (gpointer)));
+       }
+
+       for (i = 0; i < cinfo->nargs; ++i) {
+               ArgInfo *ainfo = &caller_cinfo->args [i];
+               ArgInfo *ainfo2 = &callee_cinfo->args [i];
+               int nslots;
+
+               switch (ainfo->storage) {
+               case ArgGSharedVt:
+                       if (ainfo2->storage == ArgOnStack) {
+                               nslots = callee_cinfo->args [i].nslots;
+                               if (!nslots)
+                                       nslots = 1;
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo->offset / sizeof (gpointer)) + (1 << 16) + (nslots << 18)));
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo2->offset / sizeof (gpointer))));
+                       } else {
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo->offset / sizeof (gpointer))));
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo2->offset / sizeof (gpointer))));
+                       }
+                       break;
+               default:
+                       if (ainfo2->storage == ArgOnStack) {
+                               nslots = cinfo->args [i].nslots;
+                               if (!nslots)
+                                       nslots = 1;
+                               for (j = 0; j < nslots; ++j) {
+                                       g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo->offset / sizeof (gpointer)) + j));
+                                       g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo2->offset / sizeof (gpointer)) + j));
+                               }
+                       } else {
+                               g_assert (ainfo2->storage == ArgGSharedVt);
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo->offset / sizeof (gpointer)) + (2 << 16)));
+                               g_ptr_array_add (map, GUINT_TO_POINTER ((ainfo2->offset / sizeof (gpointer))));
+                       }
+                       break;
+               }
+       }
+
+       info = mono_domain_alloc0 (mono_domain_get (), sizeof (GSharedVtCallInfo) + (map->len * sizeof (int)));
+       info->addr = addr;
+       info->stack_usage = callee_cinfo->stack_usage;
+       info->ret_marshal = GSHAREDVT_RET_NONE;
+       info->gsharedvt_in = gsharedvt_in ? 1 : 0;
+       info->vret_slot = -1;
+       info->calli = calli ? 1 : 0;
+       if (var_ret)
+               info->vret_arg_slot = gcinfo->vret_arg_offset / sizeof (gpointer);
+       else
+               info->vret_arg_slot = -1;
+       info->vcall_offset = vcall_offset;
+       info->map_count = map->len / 2;
+       for (i = 0; i < map->len; ++i)
+               info->map [i] = GPOINTER_TO_UINT (g_ptr_array_index (map, i));
+       g_ptr_array_free (map, TRUE);
+
+       /* Compute return value marshalling */
+       if (var_ret) {
+               switch (cinfo->ret.storage) {
+               case ArgInIReg:
+                       if (gsharedvt_in && !sig->ret->byref && sig->ret->type == MONO_TYPE_I1)
+                               info->ret_marshal = GSHAREDVT_RET_I1;
+                       else if (gsharedvt_in && !sig->ret->byref && (sig->ret->type == MONO_TYPE_U1 || sig->ret->type == MONO_TYPE_BOOLEAN))
+                               info->ret_marshal = GSHAREDVT_RET_U1;
+                       else if (gsharedvt_in && !sig->ret->byref && sig->ret->type == MONO_TYPE_I2)
+                               info->ret_marshal = GSHAREDVT_RET_I2;
+                       else if (gsharedvt_in && !sig->ret->byref && (sig->ret->type == MONO_TYPE_U2 || sig->ret->type == MONO_TYPE_CHAR))
+                               info->ret_marshal = GSHAREDVT_RET_U2;
+                       else if (cinfo->ret.is_pair)
+                               info->ret_marshal = GSHAREDVT_RET_IREGS;
+                       else
+                               info->ret_marshal = GSHAREDVT_RET_IREG;
+                       break;
+               case ArgOnDoubleFpStack:
+                       info->ret_marshal = GSHAREDVT_RET_DOUBLE_FPSTACK;
+                       break;
+               case ArgOnFloatFpStack:
+                       info->ret_marshal = GSHAREDVT_RET_FLOAT_FPSTACK;
+                       break;
+               case ArgOnStack:
+                       /* The caller passes in a vtype ret arg as well */
+                       g_assert (gcinfo->vtype_retaddr);
+                       /* Just have to pop the arg, as done by normal methods in their epilog */
+                       info->ret_marshal = GSHAREDVT_RET_STACK_POP;
+                       break;
+               default:
+                       g_assert_not_reached ();
+               }
+       } else if (gsharedvt_in && cinfo->vtype_retaddr) {
+               info->ret_marshal = GSHAREDVT_RET_STACK_POP;
+       }
+
+       if (gsharedvt_in && var_ret && !caller_cinfo->vtype_retaddr) {
+               /* Allocate stack space for the return value */
+               info->vret_slot = info->stack_usage / sizeof (gpointer);
+               // FIXME:
+               info->stack_usage += sizeof (gpointer) * 3;
+       }
+
+       info->stack_usage = ALIGN_TO (info->stack_usage, MONO_ARCH_FRAME_ALIGNMENT);
+
+       g_free (caller_cinfo);
+       g_free (callee_cinfo);
+
+       return info;
+}
+#endif
index 9802e46c58f88cffa1743c6a92d41085ec439774..6f2685dce80d67d586da67b8058f69e8f53d66a8 100644 (file)
@@ -9,6 +9,7 @@
  * Copyright 2003 Ximian, Inc.
  * Copyright 2003-2011 Novell Inc.
  * Copyright 2011 Xamarin Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "mini.h"
 #include <string.h>
@@ -179,49 +180,6 @@ mono_x86_patch (unsigned char* code, gpointer target)
        x86_patch (code, (unsigned char*)target);
 }
 
-typedef enum {
-       ArgInIReg,
-       ArgInFloatSSEReg,
-       ArgInDoubleSSEReg,
-       ArgOnStack,
-       ArgValuetypeInReg,
-       ArgOnFloatFpStack,
-       ArgOnDoubleFpStack,
-       /* gsharedvt argument passed by addr */
-       ArgGSharedVt,
-       ArgNone
-} ArgStorage;
-
-typedef struct {
-       gint16 offset;
-       gint8  reg;
-       ArgStorage storage;
-       int nslots;
-       gboolean is_pair;
-
-       /* Only if storage == ArgValuetypeInReg */
-       ArgStorage pair_storage [2];
-       gint8 pair_regs [2];
-} ArgInfo;
-
-typedef struct {
-       int nargs;
-       guint32 stack_usage;
-       guint32 reg_usage;
-       guint32 freg_usage;
-       gboolean need_stack_align;
-       guint32 stack_align_amount;
-       gboolean vtype_retaddr;
-       /* The index of the vret arg in the argument list */
-       int vret_arg_index;
-       int vret_arg_offset;
-       /* Argument space popped by the callee */
-       int callee_stack_pop;
-       ArgInfo ret;
-       ArgInfo sig_cookie;
-       ArgInfo args [1];
-} CallInfo;
-
 #define FLOAT_PARAM_REGS 0
 
 static const guint32 thiscall_param_regs [] = { X86_ECX, X86_NREG };
@@ -761,7 +719,7 @@ mono_arch_init (void)
 
        mono_aot_register_jit_icall ("mono_x86_throw_exception", mono_x86_throw_exception);
        mono_aot_register_jit_icall ("mono_x86_throw_corlib_exception", mono_x86_throw_corlib_exception);
-#if defined(ENABLE_GSHAREDVT)
+#if defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
        mono_aot_register_jit_icall ("mono_x86_start_gsharedvt_call", mono_x86_start_gsharedvt_call);
 #endif
 }
@@ -1052,7 +1010,9 @@ mono_arch_allocate_vars (MonoCompile *cfg)
        header = cfg->header;
        sig = mono_method_signature (cfg->method);
 
-       cinfo = get_call_info (cfg->mempool, sig);
+       if (!cfg->arch.cinfo)
+               cfg->arch.cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = (CallInfo *)cfg->arch.cinfo;
 
        cfg->frame_reg = X86_EBP;
        offset = 0;
@@ -1182,8 +1142,8 @@ mono_arch_allocate_vars (MonoCompile *cfg)
                if (inst->opcode != OP_REGVAR) {
                        inst->opcode = OP_REGOFFSET;
                        inst->inst_basereg = X86_EBP;
+                       inst->inst_offset = ainfo->offset + ARGS_OFFSET;
                }
-               inst->inst_offset = ainfo->offset + ARGS_OFFSET;
        }
 
        cfg->stack_offset = offset;
@@ -1198,7 +1158,10 @@ mono_arch_create_vars (MonoCompile *cfg)
 
        sig = mono_method_signature (cfg->method);
 
-       cinfo = get_call_info (cfg->mempool, sig);
+       if (!cfg->arch.cinfo)
+               cfg->arch.cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = (CallInfo *)cfg->arch.cinfo;
+
        sig_ret = mini_get_underlying_type (sig->ret);
 
        if (cinfo->ret.storage == ArgValuetypeInReg)
@@ -2475,26 +2438,6 @@ emit_setup_lmf (MonoCompile *cfg, guint8 *code, gint32 lmf_offset, int cfa_offse
        return code;
 }
 
-#define REAL_PRINT_REG(text,reg) \
-mono_assert (reg >= 0); \
-x86_push_reg (code, X86_EAX); \
-x86_push_reg (code, X86_EDX); \
-x86_push_reg (code, X86_ECX); \
-x86_push_reg (code, reg); \
-x86_push_imm (code, reg); \
-x86_push_imm (code, text " %d %p\n"); \
-x86_mov_reg_imm (code, X86_EAX, printf); \
-x86_call_reg (code, X86_EAX); \
-x86_alu_reg_imm (code, X86_ADD, X86_ESP, 3*4); \
-x86_pop_reg (code, X86_ECX); \
-x86_pop_reg (code, X86_EDX); \
-x86_pop_reg (code, X86_EAX);
-
-/* REAL_PRINT_REG does not appear to be used, and was not adapted to work with Native Client. */
-#ifdef __native__client_codegen__
-#define REAL_PRINT_REG(text, reg) g_assert_not_reached()
-#endif
-
 /* benchmark and set based on cpu */
 #define LOOP_ALIGNMENT 8
 #define bb_is_loop_start(bb) ((bb)->loop_body_start && (bb)->nesting)
@@ -5190,6 +5133,8 @@ mono_arch_emit_prolog (MonoCompile *cfg)
        MonoBasicBlock *bb;
        MonoMethodSignature *sig;
        MonoInst *inst;
+       CallInfo *cinfo;
+       ArgInfo *ainfo;
        int alloc_size, pos, max_offset, i, cfa_offset;
        guint8 *code;
        gboolean need_stack_frame;
@@ -5449,11 +5394,14 @@ mono_arch_emit_prolog (MonoCompile *cfg)
        sig = mono_method_signature (method);
        pos = 0;
 
+       cinfo = (CallInfo *)cfg->arch.cinfo;
+
        for (i = 0; i < sig->param_count + sig->hasthis; ++i) {
                inst = cfg->args [pos];
+               ainfo = &cinfo->args [pos];
                if (inst->opcode == OP_REGVAR) {
                        g_assert (need_stack_frame);
-                       x86_mov_reg_membase (code, inst->dreg, X86_EBP, inst->inst_offset, 4);
+                       x86_mov_reg_membase (code, inst->dreg, X86_EBP, ainfo->offset + ARGS_OFFSET, 4);
                        if (cfg->verbose_level > 2)
                                g_print ("Argument %d assigned to register %s\n", pos, mono_arch_regname (inst->dreg));
                }
@@ -5575,7 +5523,7 @@ mono_arch_emit_epilog (MonoCompile *cfg)
        }
 
        /* Load returned vtypes into registers if needed */
-       cinfo = get_call_info (cfg->mempool, sig);
+       cinfo = (CallInfo *)cfg->arch.cinfo;
        if (cinfo->ret.storage == ArgValuetypeInReg) {
                for (quad = 0; quad < 2; quad ++) {
                        switch (cinfo->ret.pair_storage [quad]) {
@@ -6826,8 +6774,8 @@ mono_arch_opcode_supported (int opcode)
        }
 }
 
-#if defined(ENABLE_GSHAREDVT)
-
-#include "../../../mono-extensions/mono/mini/mini-x86-gsharedvt.c"
-
-#endif /* !MONOTOUCH */
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig)
+{
+       return get_call_info (mp, sig);
+}
index 212f844af4ca27f1076c08c4b917081aeac08c4e..0ca2bdcec44d54524c13b56004e93c1149bb4c8c 100644 (file)
@@ -165,6 +165,7 @@ typedef struct {
        gboolean need_stack_frame_inited;
        gboolean need_stack_frame;
        int sp_fp_offset, param_area_size;
+       gpointer cinfo;
        gpointer ss_tramp_var;
        gpointer bp_tramp_var;
 } MonoCompileArch;
@@ -300,6 +301,49 @@ typedef struct {
        int map [MONO_ZERO_LEN_ARRAY];
 } GSharedVtCallInfo;
 
+typedef enum {
+       ArgInIReg,
+       ArgInFloatSSEReg,
+       ArgInDoubleSSEReg,
+       ArgOnStack,
+       ArgValuetypeInReg,
+       ArgOnFloatFpStack,
+       ArgOnDoubleFpStack,
+       /* gsharedvt argument passed by addr */
+       ArgGSharedVt,
+       ArgNone
+} ArgStorage;
+
+typedef struct {
+       gint16 offset;
+       gint8  reg;
+       ArgStorage storage;
+       int nslots;
+       gboolean is_pair;
+
+       /* Only if storage == ArgValuetypeInReg */
+       ArgStorage pair_storage [2];
+       gint8 pair_regs [2];
+} ArgInfo;
+
+typedef struct {
+       int nargs;
+       guint32 stack_usage;
+       guint32 reg_usage;
+       guint32 freg_usage;
+       gboolean need_stack_align;
+       guint32 stack_align_amount;
+       gboolean vtype_retaddr;
+       /* The index of the vret arg in the argument list */
+       int vret_arg_index;
+       int vret_arg_offset;
+       /* Argument space popped by the callee */
+       int callee_stack_pop;
+       ArgInfo ret;
+       ArgInfo sig_cookie;
+       ArgInfo args [1];
+} CallInfo;
+
 guint8*
 mono_x86_emit_tls_get (guint8* code, int dreg, int tls_offset);
 
@@ -326,5 +370,8 @@ mono_x86_patch (unsigned char* code, gpointer target);
 gpointer
 mono_x86_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg);
 
+CallInfo*
+mono_arch_get_call_info (MonoMemPool *mp, MonoMethodSignature *sig);
+
 #endif /* __MONO_MINI_X86_H__ */  
 
index 046572a332925011fdfb5b9d33a0f3ec30c14f7a..94062ec4b84ef71dcc6d6b01c97042e268f4f217 100644 (file)
@@ -8,6 +8,7 @@
  * Copyright 2002-2003 Ximian, Inc.
  * Copyright 2003-2010 Novell, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -1229,18 +1230,6 @@ mini_method_verify (MonoCompile *cfg, MonoMethod *method, gboolean fail_compile)
 
        res = mono_method_verify_with_current_settings (method, cfg->skip_visibility, is_fulltrust);
 
-       if (mono_loader_get_last_error ()) {
-               if (fail_compile) {
-                       mono_cfg_set_exception (cfg, MONO_EXCEPTION_MONO_ERROR);
-                       mono_error_set_from_loader_error (&cfg->error);
-               } else {
-                       mono_loader_clear_error ();
-               }
-               if (res)
-                       mono_free_verify_list (res);
-               return TRUE;
-       }
-
        if (res) { 
                for (tmp = res; tmp; tmp = tmp->next) {
                        MonoVerifyInfoExtended *info = (MonoVerifyInfoExtended *)tmp->data;
@@ -3733,7 +3722,11 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
         */
        mono_compile_create_vars (cfg);
 
+       mono_cfg_dump_create_context (cfg);
+       mono_cfg_dump_begin_group (cfg);
+
        MONO_TIME_TRACK (mono_jit_stats.jit_method_to_ir, i = mono_method_to_ir (cfg, method_to_compile, NULL, NULL, NULL, NULL, 0, FALSE));
+       mono_cfg_dump_ir (cfg, "method-to-ir");
 
        if (i < 0) {
                if (try_generic_shared && cfg->exception_type == MONO_EXCEPTION_GENERIC_SHARING_FAILED) {
@@ -3795,42 +3788,59 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
         * SSA will ignore variables marked VOLATILE.
         */
        MONO_TIME_TRACK (mono_jit_stats.jit_liveness_handle_exception_clauses, mono_liveness_handle_exception_clauses (cfg));
+       mono_cfg_dump_ir (cfg, "liveness_handle_exception_clauses");
 
        MONO_TIME_TRACK (mono_jit_stats.jit_handle_out_of_line_bblock, mono_handle_out_of_line_bblock (cfg));
+       mono_cfg_dump_ir (cfg, "handle_out_of_line_bblock");
 
        /*g_print ("numblocks = %d\n", cfg->num_bblocks);*/
 
        if (!COMPILE_LLVM (cfg)) {
                MONO_TIME_TRACK (mono_jit_stats.jit_decompose_long_opts, mono_decompose_long_opts (cfg));
+               mono_cfg_dump_ir (cfg, "decompose_long_opts");
        }
 
        /* Should be done before branch opts */
-       if (cfg->opt & (MONO_OPT_CONSPROP | MONO_OPT_COPYPROP))
+       if (cfg->opt & (MONO_OPT_CONSPROP | MONO_OPT_COPYPROP)) {
                MONO_TIME_TRACK (mono_jit_stats.jit_local_cprop, mono_local_cprop (cfg));
+               mono_cfg_dump_ir (cfg, "local_cprop");
+       }
 
        /*
         * Should be done after cprop which can do strength reduction on
         * some of these ops, after propagating immediates.
         */
-       if (cfg->has_emulated_ops)
+       if (cfg->has_emulated_ops) {
                MONO_TIME_TRACK (mono_jit_stats.jit_local_emulate_ops, mono_local_emulate_ops (cfg));
+               mono_cfg_dump_ir (cfg, "local_emulate_ops");
+       }
 
-       if (cfg->opt & MONO_OPT_BRANCH)
+       if (cfg->opt & MONO_OPT_BRANCH) {
                MONO_TIME_TRACK (mono_jit_stats.jit_optimize_branches, mono_optimize_branches (cfg));
+               mono_cfg_dump_ir (cfg, "optimize_branches");
+       }
 
        /* This must be done _before_ global reg alloc and _after_ decompose */
        MONO_TIME_TRACK (mono_jit_stats.jit_handle_global_vregs, mono_handle_global_vregs (cfg));
-       if (cfg->opt & MONO_OPT_DEADCE)
+       mono_cfg_dump_ir (cfg, "handle_global_vregs");
+       if (cfg->opt & MONO_OPT_DEADCE) {
                MONO_TIME_TRACK (mono_jit_stats.jit_local_deadce, mono_local_deadce (cfg));
-       if (cfg->opt & MONO_OPT_ALIAS_ANALYSIS)
+               mono_cfg_dump_ir (cfg, "local_deadce");
+       }
+       if (cfg->opt & MONO_OPT_ALIAS_ANALYSIS) {
                MONO_TIME_TRACK (mono_jit_stats.jit_local_alias_analysis, mono_local_alias_analysis (cfg));
+               mono_cfg_dump_ir (cfg, "local_alias_analysis");
+       }
        /* Disable this for LLVM to make the IR easier to handle */
-       if (!COMPILE_LLVM (cfg))
+       if (!COMPILE_LLVM (cfg)) {
                MONO_TIME_TRACK (mono_jit_stats.jit_if_conversion, mono_if_conversion (cfg));
+               mono_cfg_dump_ir (cfg, "if_conversion");
+       }
 
        mono_threads_safepoint ();
 
        MONO_TIME_TRACK (mono_jit_stats.jit_bb_ordering, mono_bb_ordering (cfg));
+       mono_cfg_dump_ir (cfg, "bb_ordering");
 
        if (((cfg->num_varinfo > 2000) || (cfg->num_bblocks > 1000)) && !cfg->compile_aot) {
                /* 
@@ -3848,6 +3858,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
        }
 
        MONO_TIME_TRACK (mono_jit_stats.jit_insert_safepoints, mono_insert_safepoints (cfg));
+       mono_cfg_dump_ir (cfg, "insert_safepoints");
 
        /* after method_to_ir */
        if (parts == 1) {
@@ -3877,6 +3888,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
                if (!(cfg->comp_done & MONO_COMP_SSA) && !cfg->disable_ssa) {
 #ifndef DISABLE_SSA
                        MONO_TIME_TRACK (mono_jit_stats.jit_ssa_compute, mono_ssa_compute (cfg));
+                       mono_cfg_dump_ir (cfg, "ssa_compute");
 #endif
 
                        if (cfg->verbose_level >= 2) {
@@ -3897,6 +3909,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
                if (cfg->comp_done & MONO_COMP_SSA && !COMPILE_LLVM (cfg)) {
 #ifndef DISABLE_SSA
                        MONO_TIME_TRACK (mono_jit_stats.jit_ssa_cprop, mono_ssa_cprop (cfg));
+                       mono_cfg_dump_ir (cfg, "ssa_cprop");
 #endif
                }
        }
@@ -3905,28 +3918,42 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
        if (cfg->comp_done & MONO_COMP_SSA && !COMPILE_LLVM (cfg)) {
                //mono_ssa_strength_reduction (cfg);
 
-               if (cfg->opt & MONO_OPT_DEADCE)
+               if (cfg->opt & MONO_OPT_DEADCE) {
                        MONO_TIME_TRACK (mono_jit_stats.jit_ssa_deadce, mono_ssa_deadce (cfg));
+                       mono_cfg_dump_ir (cfg, "ssa_deadce");
+               }
 
-               if ((cfg->flags & (MONO_CFG_HAS_LDELEMA|MONO_CFG_HAS_CHECK_THIS)) && (cfg->opt & MONO_OPT_ABCREM))
+               if ((cfg->flags & (MONO_CFG_HAS_LDELEMA|MONO_CFG_HAS_CHECK_THIS)) && (cfg->opt & MONO_OPT_ABCREM)) {
                        MONO_TIME_TRACK (mono_jit_stats.jit_perform_abc_removal, mono_perform_abc_removal (cfg));
+                       mono_cfg_dump_ir (cfg, "perform_abc_removal");
+               }
 
                MONO_TIME_TRACK (mono_jit_stats.jit_ssa_remove, mono_ssa_remove (cfg));
+               mono_cfg_dump_ir (cfg, "ssa_remove");
                MONO_TIME_TRACK (mono_jit_stats.jit_local_cprop2, mono_local_cprop (cfg));
+               mono_cfg_dump_ir (cfg, "local_cprop2");
                MONO_TIME_TRACK (mono_jit_stats.jit_handle_global_vregs2, mono_handle_global_vregs (cfg));
-               if (cfg->opt & MONO_OPT_DEADCE)
+               mono_cfg_dump_ir (cfg, "handle_global_vregs2");
+               if (cfg->opt & MONO_OPT_DEADCE) {
                        MONO_TIME_TRACK (mono_jit_stats.jit_local_deadce2, mono_local_deadce (cfg));
+                       mono_cfg_dump_ir (cfg, "local_deadce2");
+               }
 
-               if (cfg->opt & MONO_OPT_BRANCH)
+               if (cfg->opt & MONO_OPT_BRANCH) {
                        MONO_TIME_TRACK (mono_jit_stats.jit_optimize_branches2, mono_optimize_branches (cfg));
+                       mono_cfg_dump_ir (cfg, "optimize_branches2");
+               }
        }
 #endif
 
        if (cfg->comp_done & MONO_COMP_SSA && COMPILE_LLVM (cfg)) {
                mono_ssa_loop_invariant_code_motion (cfg);
+               mono_cfg_dump_ir (cfg, "loop_invariant_code_motion");
                /* This removes MONO_INST_FAULT flags too so perform it unconditionally */
-               if (cfg->opt & MONO_OPT_ABCREM)
+               if (cfg->opt & MONO_OPT_ABCREM) {
                        mono_perform_abc_removal (cfg);
+                       mono_cfg_dump_ir (cfg, "abc_removal");
+               }
        }
 
        /* after SSA removal */
@@ -3944,8 +3971,10 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
                mono_decompose_soft_float (cfg);
 #endif
        MONO_TIME_TRACK (mono_jit_stats.jit_decompose_vtype_opts, mono_decompose_vtype_opts (cfg));
-       if (cfg->flags & MONO_CFG_HAS_ARRAY_ACCESS)
+       if (cfg->flags & MONO_CFG_HAS_ARRAY_ACCESS) {
                MONO_TIME_TRACK (mono_jit_stats.jit_decompose_array_access_opts, mono_decompose_array_access_opts (cfg));
+               mono_cfg_dump_ir (cfg, "decompose_array_access_opts");
+       }
 
        if (cfg->got_var) {
 #ifndef MONO_ARCH_GOT_REG
@@ -4000,6 +4029,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
                                }
                        }
                        MONO_TIME_TRACK (mono_jit_stats.jit_linear_scan, mono_linear_scan (cfg, vars, regs, &cfg->used_int_regs));
+                       mono_cfg_dump_ir (cfg, "linear_scan");
                }
        }
 
@@ -4010,6 +4040,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
        /* variables are allocated after decompose, since decompose could create temps */
        if (!COMPILE_LLVM (cfg)) {
                MONO_TIME_TRACK (mono_jit_stats.jit_arch_allocate_vars, mono_arch_allocate_vars (cfg));
+               mono_cfg_dump_ir (cfg, "arch_allocate_vars");
                if (cfg->exception_type)
                        return cfg;
        }
@@ -4020,12 +4051,14 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
        if (!COMPILE_LLVM (cfg)) {
                gboolean need_local_opts;
                MONO_TIME_TRACK (mono_jit_stats.jit_spill_global_vars, mono_spill_global_vars (cfg, &need_local_opts));
+               mono_cfg_dump_ir (cfg, "spill_global_vars");
 
                if (need_local_opts || cfg->compile_aot) {
                        /* To optimize code created by spill_global_vars */
                        MONO_TIME_TRACK (mono_jit_stats.jit_local_cprop3, mono_local_cprop (cfg));
                        if (cfg->opt & MONO_OPT_DEADCE)
                                MONO_TIME_TRACK (mono_jit_stats.jit_local_deadce3, mono_local_deadce (cfg));
+                       mono_cfg_dump_ir (cfg, "needs_local_opts");
                }
        }
 
@@ -4071,6 +4104,7 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
 #endif
        } else {
                MONO_TIME_TRACK (mono_jit_stats.jit_codegen, mono_codegen (cfg));
+               mono_cfg_dump_ir (cfg, "codegen");
                if (cfg->exception_type)
                        return cfg;
        }
@@ -4140,6 +4174,8 @@ mini_method_compile (MonoMethod *method, guint32 opts, MonoDomain *domain, JitFl
        if (MONO_METHOD_COMPILE_END_ENABLED ())
                MONO_PROBE_METHOD_COMPILE_END (method, TRUE);
 
+       mono_cfg_dump_close_group (cfg);
+
        return cfg;
 }
 
@@ -4374,7 +4410,8 @@ mono_jit_compile_method_inner (MonoMethod *method, MonoDomain *target_domain, in
        case MONO_EXCEPTION_MISSING_FIELD:
        case MONO_EXCEPTION_MISSING_METHOD:
        case MONO_EXCEPTION_FILE_NOT_FOUND:
-       case MONO_EXCEPTION_BAD_IMAGE: {
+       case MONO_EXCEPTION_BAD_IMAGE:
+       case MONO_EXCEPTION_INVALID_PROGRAM: {
                /* Throw a type load exception if needed */
                if (cfg->exception_ptr) {
                        ex = mono_class_get_exception_for_failure ((MonoClass *)cfg->exception_ptr);
@@ -4389,6 +4426,8 @@ mono_jit_compile_method_inner (MonoMethod *method, MonoDomain *target_domain, in
                                ex = mono_exception_from_name_msg (mono_defaults.corlib, "System.IO", "FileNotFoundException", cfg->exception_message);
                        else if (cfg->exception_type == MONO_EXCEPTION_BAD_IMAGE)
                                ex = mono_get_exception_bad_image_format (cfg->exception_message);
+                       else if (cfg->exception_type == MONO_EXCEPTION_INVALID_PROGRAM)
+                               ex = mono_exception_from_name_msg (mono_defaults.corlib, "System", "InvalidProgramException", cfg->exception_message);
                        else
                                g_assert_not_reached ();
                }
index 2a1b331f809921750df32acc131c984005861ce1..3159149307040796ecef73de4c5a6fc3ae92d7e5 100644 (file)
@@ -2,6 +2,7 @@
  * Copyright 2002-2003 Ximian Inc
  * Copyright 2003-2011 Novell Inc
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_MINI_H__
 #define __MONO_MINI_H__
@@ -39,6 +40,7 @@
 #include "regalloc.h"
 #include "mini-unwind.h"
 #include "jit.h"
+#include "cfgdump.h"
 
 #include "mono/metadata/class-internals.h"
 #include "mono/metadata/domain-internals.h"
@@ -1842,6 +1844,9 @@ typedef struct {
        /* Error handling */
        MonoError error;
 
+       /* pointer to context datastructure used for graph dumping */
+       MonoGraphDumper *gdump_ctx;
+
        /* Stats */
        int stat_allocate_var;
        int stat_locals_stack_size;
@@ -2281,11 +2286,19 @@ mono_bb_last_inst (MonoBasicBlock *bb, int filter)
 MONO_API int         mono_main                      (int argc, char* argv[]);
 MONO_API void        mono_set_defaults              (int verbose_level, guint32 opts);
 MONO_API void        mono_parse_env_options         (int *ref_argc, char **ref_argv []);
+MONO_API char       *mono_parse_options_from        (const char *options, int *ref_argc, char **ref_argv []);
+
 MonoDomain* mini_init                      (const char *filename, const char *runtime_version);
 void        mini_cleanup                   (MonoDomain *domain);
 MONO_API MonoDebugOptions *mini_get_debug_options   (void);
 MONO_API gboolean    mini_parse_debug_option (const char *option);
 
+/* graph dumping */
+void mono_cfg_dump_create_context (MonoCompile *cfg);
+void mono_cfg_dump_begin_group (MonoCompile *cfg);
+void mono_cfg_dump_close_group (MonoCompile *cfg);
+void mono_cfg_dump_ir (MonoCompile *cfg, const char *phase_name);
+
 /* helper methods */
 void      mini_jit_init                    (void);
 void      mini_jit_cleanup                 (void);
@@ -2341,6 +2354,7 @@ void      mono_blockset_print               (MonoCompile *cfg, MonoBitSet *set,
 const char*mono_ji_type_to_string           (MonoJumpInfoType type);
 void      mono_print_ji                     (const MonoJumpInfo *ji);
 void      mono_print_ins_index              (int i, MonoInst *ins);
+GString  *mono_print_ins_index_strbuf       (int i, MonoInst *ins);
 void      mono_print_ins                    (MonoInst *ins);
 void      mono_print_bb                     (MonoBasicBlock *bb, const char *msg);
 void      mono_print_code                   (MonoCompile *cfg, const char *msg);
@@ -3009,6 +3023,10 @@ mono_method_is_generic_sharable_full (MonoMethod *method, gboolean allow_type_va
 gboolean
 mini_class_is_generic_sharable (MonoClass *klass);
 
+
+gboolean
+mini_generic_inst_is_sharable (MonoGenericInst *inst, gboolean allow_type_vars, gboolean allow_partial);
+
 gboolean
 mono_is_partially_sharable_inst (MonoGenericInst *inst);
 
@@ -3189,4 +3207,10 @@ gboolean MONO_SIG_HANDLER_SIGNATURE (mono_chain_signal);
 #define ARCH_VARARG_ICALLS 0
 #endif
 
+/*
+ * Native unwinder integration
+ */
+void mono_exception_native_unwind (void *ctx, MONO_SIG_HANDLER_INFO_TYPE *info);
+
+
 #endif /* __MONO_MINI_H__ */
index 434a11f43702db5e180d652eac020f06740566db..fd9cc01200d0c9d3ba020853ac7b3f39e9a38732 100644 (file)
@@ -5,6 +5,7 @@
  *   Marcos Henrich (marcos.henrich@xamarin.com)
  *
  * Copyright 2014 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mini.h"
index d0e6f5aa1575f5fd87bde866a4d8fc31a51eea50..79915205a2d7e25bcd94b944edff81803fc48474 100644 (file)
@@ -1,5 +1,6 @@
 /*
  * Copyright 2014 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
  
 #ifndef __MONO_SEQ_POINTS_H__
index a29108872a4adbb4dfb50430f70595a6eb3c9b17..cb100267ef706a6c3608f7b09e12f5dcb92e1cfb 100644 (file)
@@ -6,6 +6,7 @@
  *
  * (C) 2003 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 #include <string.h>
index eb42a0279c1faf464a2b0840c7a8b611d95a4a2b..45d32b99c05e54b64969afac9b9c51d6047a07b8 100755 (executable)
@@ -6,7 +6,12 @@ USE_AOT=$2
 TMP_FILE_PREFIX=$(basename $0).tmp
 BASEDIR=$(dirname $0)
 
-MONO_PATH=$BASEDIR/../../mcs/class/lib/net_4_x:$BASEDIR
+case "$(uname -s)" in
+       CYGWIN*) PLATFORM_PATH_SEPARATOR=';';;
+       *) PLATFORM_PATH_SEPARATOR=':';;
+esac
+
+MONO_PATH=$BASEDIR/../../mcs/class/lib/net_4_x$PLATFORM_PATH_SEPARATOR$BASEDIR
 RUNTIME=$BASEDIR/../../runtime/mono-wrapper
 
 trap "rm -rf ${TMP_FILE_PREFIX}*" EXIT
@@ -16,7 +21,7 @@ tmp_file () {
 }
 
 clean_aot () {
-       rm -rf *.exe.so *.exe.dylib *.exe.dylib.dSYM
+       rm -rf *.exe.so *.exe.dylib *.exe.dylib.dSYM *.exe.dll
 }
 
 # The test compares the generated native code size between a compilation with and without seq points.
@@ -42,15 +47,19 @@ get_method () {
 }
 
 diff_methods () {
-       TMP_FILE=$(tmp_file)
-       echo "$(MONO_DEBUG=single-imm-size get_methods $1 $2 $3 $4)" >$TMP_FILE
-       diff <(cat $TMP_FILE) <(echo "$(MONO_DEBUG=gen-compact-seq-points,single-imm-size get_methods $1 $2 $3 $4)")
+       TMP_FILE1=$(tmp_file)
+       TMP_FILE2=$(tmp_file)
+       echo "$(MONO_DEBUG=single-imm-size get_methods $1 $2 $3 $4)" >$TMP_FILE1
+       echo "$(MONO_DEBUG=gen-compact-seq-points,single-imm-size get_methods $1 $2 $3 $4)" >$TMP_FILE2
+       diff $TMP_FILE1 $TMP_FILE2
 }
 
 diff_method () {
-       TMP_FILE=$(tmp_file)
-       echo "$(MONO_DEBUG=single-imm-size get_method $1 $2 $3 $4 $5)" >$TMP_FILE
-       sdiff -w 150 <(cat $TMP_FILE) <(echo "$(MONO_DEBUG=gen-compact-seq-points,single-imm-size get_method $1 $2 $3 $4 $5 | grep -Ev il_seq_point)")
+       TMP_FILE1=$(tmp_file)
+       TMP_FILE2=$(tmp_file)
+       echo "$(MONO_DEBUG=single-imm-size get_method $1 $2 $3 $4 $5)" >$TMP_FILE1
+       echo "$(MONO_DEBUG=gen-compact-seq-points,single-imm-size get_method $1 $2 $3 $4 $5 | grep -Ev il_seq_point)" >$TMP_FILE2
+       sdiff -w 150 $TMP_FILE1 $TMP_FILE2
 }
 
 get_method_name () {
index 765bc111c09bb22e86740bdc03f19ff6b4bf29fb..d8e4437b75d5ddb7836dbee0230e052f673744d6 100644 (file)
@@ -7,6 +7,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
diff --git a/mono/mini/tramp-amd64-gsharedvt.c b/mono/mini/tramp-amd64-gsharedvt.c
new file mode 100644 (file)
index 0000000..675dcf6
--- /dev/null
@@ -0,0 +1,469 @@
+/*
+ * tramp-amd64-gsharedvt.c: libcorkscrew-based native unwinder
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *   Rodrigo Kumpera <kumpera@gmail.com>
+ *   Andi McClure <andi.mcclure@xamarin.com>
+ *
+ * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <config.h>
+#include <glib.h>
+
+#include <mono/metadata/abi-details.h>
+#include <mono/metadata/appdomain.h>
+#include <mono/metadata/marshal.h>
+#include <mono/metadata/tabledefs.h>
+#include <mono/metadata/mono-debug-debugger.h>
+#include <mono/metadata/profiler-private.h>
+#include <mono/metadata/gc-internals.h>
+#include <mono/arch/amd64/amd64-codegen.h>
+
+#include <mono/utils/memcheck.h>
+
+#include "mini.h"
+#include "mini-amd64.h"
+#include "mini-amd64-gsharedvt.h"
+#include "debugger-agent.h"
+
+#if defined (MONO_ARCH_GSHAREDVT_SUPPORTED)
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+#define SRC_REG_SHIFT 0
+#define SRC_REG_MASK 0xFFFF
+
+#define SRC_DESCRIPTOR_MARSHAL_SHIFT 16
+#define SRC_DESCRIPTOR_MARSHAL_MASK 0x0FF
+
+#define SLOT_COUNT_SHIFT 24
+#define SLOT_COUNT_MASK 0xFF
+
+gpointer
+mono_amd64_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       int i;
+
+#ifdef DEBUG_AMD64_GSHAREDVT
+       printf ("mono_amd64_start_gsharedvt_call info %p caller %p callee %p ctx %p\n", info, caller, callee, mrgctx_reg);
+
+       for (i = 0; i < PARAM_REGS; ++i)
+               printf ("\treg [%d] -> %p\n", i, caller [i]);
+#endif
+
+       /* Set vtype ret arg */
+       if (info->vret_slot != -1) {
+               DEBUG_AMD64_GSHAREDVT_PRINT ("vret handling\n[%d] < &%d (%p)\n", info->vret_arg_reg, info->vret_slot, &callee [info->vret_slot]);
+               g_assert (info->vret_slot);
+               callee [info->vret_arg_reg] = &callee [info->vret_slot];
+       }
+
+       for (i = 0; i < info->map_count; ++i) {
+               int src = info->map [i * 2];
+               int dst = info->map [(i * 2) + 1];
+               int arg_marshal = (src >> SRC_DESCRIPTOR_MARSHAL_SHIFT) & SRC_DESCRIPTOR_MARSHAL_MASK;
+
+               int source_reg = src & SRC_REG_MASK;
+               int dest_reg = dst & SRC_REG_MASK;
+
+               DEBUG_AMD64_GSHAREDVT_PRINT ("source %x dest %x marshal %d: ", src, dst, arg_marshal);
+               switch (arg_marshal) {
+               case GSHAREDVT_ARG_NONE:
+                       callee [dest_reg] = caller [source_reg];
+                       DEBUG_AMD64_GSHAREDVT_PRINT ("[%d] <- %d (%p) <- (%p)\n", dest_reg, source_reg, &callee [dest_reg], caller [source_reg]);
+                       break;
+               case GSHAREDVT_ARG_BYVAL_TO_BYREF:
+                       /* gsharedvt argument passed by addr in reg/stack slot */
+                       callee [dest_reg] = &caller [source_reg];
+                       DEBUG_AMD64_GSHAREDVT_PRINT ("[%d] <- &%d (%p) <- (%p)\n", dest_reg, source_reg, &callee [dest_reg], &caller [source_reg]);
+                       break;
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL: {
+                       int slot_count = (src >> SLOT_COUNT_SHIFT) & SLOT_COUNT_MASK;
+                       int j;
+                       gpointer *addr = caller [source_reg];
+
+                       for (j = 0; j < slot_count; ++j)
+                               callee [dest_reg + j] = addr [j];
+                       DEBUG_AMD64_GSHAREDVT_PRINT ("[%d] <- [%d] (%d words) (%p) <- (%p)\n", dest_reg, source_reg, slot_count, &callee [dest_reg], &caller [source_reg]);
+                       break;
+               }
+               default:
+                       g_error ("cant handle arg marshal %d\n", arg_marshal);
+               }
+       }
+
+       //Can't handle for now
+       if (info->vcall_offset != -1){
+               MonoObject *this_obj = caller [0];
+
+               DEBUG_AMD64_GSHAREDVT_PRINT ("target is a vcall at offset %d\n", info->vcall_offset / 8);
+               if (G_UNLIKELY (!this_obj))
+                       return NULL;
+               if (info->vcall_offset == MONO_GSHAREDVT_DEL_INVOKE_VT_OFFSET)
+                       /* delegate invoke */
+                       return ((MonoDelegate*)this_obj)->invoke_impl;
+               else
+                       return *(gpointer*)((char*)this_obj->vtable + info->vcall_offset);
+       } else if (info->calli) {
+               /* The address to call is passed in the mrgctx reg */
+               return mrgctx_reg;
+       } else {
+               DEBUG_AMD64_GSHAREDVT_PRINT ("target is %p\n", info->addr);
+               return info->addr;
+       }
+}
+
+#ifndef DISABLE_JIT
+
+// Compiler support
+
+/*
+ * mono_arch_get_gsharedvt_arg_trampoline:
+ *
+ *   See tramp-x86.c for documentation.
+ */
+gpointer
+mono_arch_get_gsharedvt_arg_trampoline (MonoDomain *domain, gpointer arg, gpointer addr)
+{
+       guint8 *code, *start;
+       int buf_len;
+
+       buf_len = 32;
+
+       start = code = mono_domain_code_reserve (domain, buf_len);
+
+       amd64_mov_reg_imm (code, AMD64_RAX, arg);
+       amd64_jump_code (code, addr);
+       g_assert ((code - start) < buf_len);
+
+       nacl_domain_code_validate (domain, &start, buf_len, &code);
+       mono_arch_flush_icache (start, code - start);
+       mono_profiler_code_buffer_new (start, code - start, MONO_PROFILER_CODE_BUFFER_GENERICS_TRAMPOLINE, NULL);
+
+       g_assert (0);
+       return start;
+}
+
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int buf_len, cfa_offset;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+       int n_arg_regs, n_arg_fregs, framesize, i;
+       int info_offset, offset, rgctx_arg_reg_offset;
+       int caller_reg_area_offset, callee_reg_area_offset, callee_stack_area_offset;
+       guint8 *br_out, *br [64], *br_ret [64];
+       int b_ret_index;
+       int reg_area_size;
+
+       buf_len = 2048;
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       /*
+        * We are being called by an gsharedvt arg trampoline, the info argument is in AMD64_RAX.
+        */
+       n_arg_regs = PARAM_REGS;
+       n_arg_fregs = FLOAT_PARAM_REGS;
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* info reg */
+       info_offset = offset;
+       offset += 8;
+
+       /* rgctx reg */
+       rgctx_arg_reg_offset = offset;
+       offset += 8;
+
+       /*callconv in regs */
+       caller_reg_area_offset = offset;
+       reg_area_size = ALIGN_TO ((n_arg_regs + n_arg_fregs) * 8, MONO_ARCH_FRAME_ALIGNMENT);
+       offset += reg_area_size;
+
+       framesize = offset;
+
+       g_assert (framesize % MONO_ARCH_FRAME_ALIGNMENT == 0);
+       g_assert (reg_area_size % MONO_ARCH_FRAME_ALIGNMENT == 0);
+
+       /* unwind markers 1/3 */
+       cfa_offset = sizeof (gpointer);
+       mono_add_unwind_op_def_cfa (unwind_ops, code, buf, AMD64_RSP, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, AMD64_RIP, -cfa_offset);
+
+       /* save the old frame pointer */
+       amd64_push_reg (code, AMD64_RBP);
+
+       /* unwind markers 2/3 */
+       cfa_offset += sizeof (gpointer);
+       mono_add_unwind_op_def_cfa_offset (unwind_ops, code, buf, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, AMD64_RBP, - cfa_offset);
+
+       /* set it as the new frame pointer */
+       amd64_mov_reg_reg (code, AMD64_RBP, AMD64_RSP, sizeof(mgreg_t));
+
+       /* unwind markers 3/3 */
+       mono_add_unwind_op_def_cfa_reg (unwind_ops, code, buf, AMD64_RBP);
+
+       /* setup the frame */
+       amd64_alu_reg_imm (code, X86_SUB, AMD64_RSP, framesize);
+       
+       /* save stuff */
+
+       /* save info */
+       amd64_mov_membase_reg (code, AMD64_RSP, info_offset, AMD64_RAX, sizeof (mgreg_t));
+       /* save rgctx */
+       amd64_mov_membase_reg (code, AMD64_RSP, rgctx_arg_reg_offset, MONO_ARCH_RGCTX_REG, sizeof (mgreg_t));
+
+       for (i = 0; i < n_arg_regs; ++i)
+               amd64_mov_membase_reg (code, AMD64_RSP, caller_reg_area_offset + i * 8, param_regs [i], sizeof (mgreg_t));
+
+       for (i = 0; i < n_arg_fregs; ++i)
+               amd64_sse_movsd_membase_reg (code, AMD64_RSP, caller_reg_area_offset + (i + n_arg_regs) * 8, i);
+
+       /* TODO Allocate stack area used to pass arguments to the method */
+
+
+       /* Allocate callee register area just below the caller area so it can be accessed from start_gsharedvt_call using negative offsets */
+       /* XXX figure out alignment */
+       callee_reg_area_offset = reg_area_size - ((n_arg_regs + n_arg_fregs) * 8); /* Ensure alignment */
+       callee_stack_area_offset = callee_reg_area_offset + reg_area_size;
+       amd64_alu_reg_imm (code, X86_SUB, AMD64_RSP, reg_area_size);
+
+       /* Allocate stack area used to pass arguments to the method */
+       amd64_mov_reg_membase (code, AMD64_R11, AMD64_RAX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, stack_usage), 4);
+       amd64_alu_reg_reg (code, X86_SUB, AMD64_RSP, AMD64_R11);
+
+       /* The stack now looks like this:
+
+       <caller stack params area>
+       <return address>
+       <old frame pointer>
+       <caller registers area>
+       <rgctx>
+       <gsharedvt info>
+       <calee stack area>
+       <calee reg area>
+        */
+
+       /* Call start_gsharedvt_call () */
+       /* arg1 == info */
+       amd64_mov_reg_reg (code, MONO_AMD64_ARG_REG1, AMD64_RAX, sizeof(mgreg_t));
+       /* arg2 = caller stack area */
+       amd64_lea_membase (code, MONO_AMD64_ARG_REG2, AMD64_RBP, -(framesize - caller_reg_area_offset)); 
+
+       /* arg3 == callee stack area */
+       amd64_lea_membase (code, MONO_AMD64_ARG_REG3, AMD64_RSP, callee_reg_area_offset);
+
+       /* arg4 = mrgctx reg */
+       amd64_mov_reg_reg (code, MONO_AMD64_ARG_REG4, MONO_ARCH_RGCTX_REG, sizeof(mgreg_t));
+
+       if (aot) {
+               code = mono_arch_emit_load_aotconst (buf, code, &ji, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_amd64_start_gsharedvt_call");
+               amd64_call_reg (code, AMD64_R11);
+       } else {
+               g_error ("no aot");
+       }
+
+       /* Method to call is now on RAX. Restore regs and jump */
+       amd64_mov_reg_reg (code, AMD64_R11, AMD64_RAX, sizeof(mgreg_t));
+
+       for (i = 0; i < n_arg_regs; ++i)
+               amd64_mov_reg_membase (code, param_regs [i], AMD64_RSP, callee_reg_area_offset + i * 8, sizeof (mgreg_t));
+
+       for (i = 0; i < n_arg_fregs; ++i)
+               amd64_sse_movsd_reg_membase (code, i, AMD64_RSP, callee_reg_area_offset + (i + n_arg_regs) * 8);
+
+       //load rgctx
+       amd64_mov_reg_membase (code, MONO_ARCH_RGCTX_REG, AMD64_RBP, -(framesize - rgctx_arg_reg_offset), sizeof (mgreg_t));
+
+       /* Clear callee reg area */
+       amd64_alu_reg_imm (code, X86_ADD, AMD64_RSP, reg_area_size);
+
+       /* Call the thing */
+       amd64_call_reg (code, AMD64_R11);
+
+       /* Marshal return value. Available registers: R10 and R11 */
+       /* Load info struct */
+       amd64_mov_reg_membase (code, AMD64_R10, AMD64_RBP, -(framesize - info_offset), sizeof (mgreg_t));
+
+       /* Branch to the in/out handling code */
+       amd64_alu_membase_imm_size (code, X86_CMP, AMD64_R10, MONO_STRUCT_OFFSET (GSharedVtCallInfo, gsharedvt_in), 1, 4);
+
+       b_ret_index = 0;
+       br_out = code;
+       x86_branch32 (code, X86_CC_NE, 0, TRUE);
+
+       /*
+        * IN CASE
+        */
+
+       /* Load vret_slot */
+       amd64_mov_reg_membase (code, AMD64_RDI, AMD64_R10, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_slot), 4);
+       amd64_alu_reg_imm (code, X86_SUB, AMD64_RDI, n_arg_regs + n_arg_fregs);
+       amd64_shift_reg_imm (code, X86_SHL, AMD64_RDI, 3);
+
+       /* vret address is RBP - (framesize - caller_reg_area_offset) */
+       amd64_mov_reg_reg (code, AMD64_R11, AMD64_RSP, sizeof(mgreg_t));
+       amd64_alu_reg_reg (code, X86_ADD, AMD64_R11, AMD64_RDI);
+
+       /* Load ret marshal type */
+       /* Load vret address in R11 */
+       amd64_mov_reg_membase (code, AMD64_R10, AMD64_R10, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal), 4);
+
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               amd64_alu_reg_imm (code, X86_CMP, AMD64_R10, i);
+               br [i] = code;
+               amd64_branch8 (code, X86_CC_EQ, 0, TRUE);
+       }
+       x86_breakpoint (code); /* unhandled case */
+
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               mono_amd64_patch (br [i], code);
+               switch (i) {
+               case GSHAREDVT_RET_NONE:
+                       break;
+               case GSHAREDVT_RET_I1:
+                       amd64_widen_membase (code, AMD64_RAX, AMD64_R11, 0, TRUE, FALSE);
+                       break;
+               case GSHAREDVT_RET_U1:
+                       amd64_widen_membase (code, AMD64_RAX, AMD64_R11, 0, FALSE, FALSE);
+                       break;
+               case GSHAREDVT_RET_I2:
+                       amd64_widen_membase (code, AMD64_RAX, AMD64_R11, 0, TRUE, TRUE);
+                       break;
+               case GSHAREDVT_RET_U2:
+                       amd64_widen_membase (code, AMD64_RAX, AMD64_R11, 0, FALSE, TRUE);
+                       break;
+               case GSHAREDVT_RET_I4: // CORRECT
+               case GSHAREDVT_RET_U4: // THIS IS INCORRECT. WHY IS IT NOT FAILING?
+                       amd64_movsxd_reg_membase (code, AMD64_RAX, AMD64_R11, 0);
+                       break;
+               case GSHAREDVT_RET_I8:
+                       amd64_mov_reg_membase (code, AMD64_RAX, AMD64_R11, 0, 8);
+                       break;
+               case GSHAREDVT_RET_IREGS_1:
+                       amd64_mov_reg_membase (code, return_regs [i - GSHAREDVT_RET_IREGS_1], AMD64_R11, 0, 8);
+                       break;
+               case GSHAREDVT_RET_R8:
+                       amd64_sse_movsd_reg_membase (code, AMD64_XMM0, AMD64_R11, 0);
+                       break;
+               default:
+                       x86_breakpoint (code); /* can't handle specific case */
+               }
+
+               br_ret [b_ret_index ++] = code;
+               x86_jump32 (code, 0);
+       }
+
+       /*
+        * OUT CASE
+        */
+       mono_amd64_patch (br_out, code);
+
+       /*
+               Address to write return to is in the original value of the register specified by vret_arg_reg.
+               This will be either RSI or RDI depending on whether this is a static call.
+               Its location:
+               We alloc 'framesize' bytes below RBP to save regs, info and rgctx. RSP = RBP - framesize
+               We store rdi at RSP + caller_reg_area_offset + slot_index_of (register) * 8.
+
+               address: RBP - framesize + caller_reg_area_offset + 8*slot
+       */
+
+       int caller_vret_offset = caller_reg_area_offset - framesize;
+
+       /* Load vret address in R11 */
+       /* Position to return to is passed as a hidden argument. Load 'vret_arg_slot' to find it */
+       amd64_movsxd_reg_membase (code, AMD64_R11, AMD64_R10, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_arg_reg));
+
+       // In the GSHAREDVT_RET_NONE case, vret_arg_slot is -1. In this case, skip marshalling.
+       amd64_alu_reg_imm (code, X86_CMP, AMD64_R11, 0);
+       br_ret [b_ret_index ++] = code;
+       amd64_branch32 (code, X86_CC_LT, 0, TRUE);
+
+       /* Compute ret area address in the caller frame, *( ((gpointer *)RBP) [R11+2] ) */
+       amd64_shift_reg_imm (code, X86_SHL, AMD64_R11, 3);
+       amd64_alu_reg_imm (code, X86_ADD, AMD64_R11, caller_vret_offset);
+       amd64_alu_reg_reg (code, X86_ADD, AMD64_R11, AMD64_RBP);
+       amd64_mov_reg_membase (code, AMD64_R11, AMD64_R11, 0, sizeof (gpointer));
+
+       /* Load ret marshal type in R10 */
+       amd64_mov_reg_membase (code, AMD64_R10, AMD64_R10, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal), 4);
+
+       // Switch table for ret_marshal value
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               amd64_alu_reg_imm (code, X86_CMP, AMD64_R10, i);
+               br [i] = code;
+               amd64_branch8 (code, X86_CC_EQ, 0, TRUE);
+       }
+       x86_breakpoint (code); /* unhandled case */
+
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               mono_amd64_patch (br [i], code);
+               switch (i) {
+               case GSHAREDVT_RET_NONE:
+                       break;
+               case GSHAREDVT_RET_IREGS_1:
+                       amd64_mov_membase_reg (code, AMD64_R11, 0, return_regs [i - GSHAREDVT_RET_IREGS_1], 8);
+                       break;
+               case GSHAREDVT_RET_R8:
+                       amd64_sse_movsd_membase_reg (code, AMD64_R11, 0, AMD64_XMM0);
+                       break;
+               default:
+                       x86_breakpoint (code); /* can't handle specific case */
+               }
+
+               br_ret [b_ret_index ++] = code;
+               x86_jump32 (code, 0);
+       }
+
+       /* exit path */
+       for (i = 0; i < b_ret_index; ++i)
+               mono_amd64_patch (br_ret [i], code);
+
+       /* Exit code path */
+       amd64_leave (code);
+       amd64_ret (code);
+
+       g_assert ((code - buf) < buf_len);
+
+       if (info)
+               *info = mono_tramp_info_create ("gsharedvt_trampoline", buf, code - buf, ji, unwind_ops);
+
+       mono_arch_flush_icache (buf, code - buf);
+       return buf;
+}
+
+#else
+
+gpointer
+mono_arch_get_gsharedvt_arg_trampoline (MonoDomain *domain, gpointer arg, gpointer addr)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif
+
+#else
+
+gpointer
+mono_amd64_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif
\ No newline at end of file
index a5ba7000e4089c1607a0dc8ccfb9747f8e6944ac..05fb2cecac28d58dd2f4146a7bc60ec6d434763c 100644 (file)
@@ -8,6 +8,7 @@
  * (C) 2001 Ximian, Inc.
  * Copyright 2003-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -1009,32 +1010,3 @@ mono_arch_create_sdb_trampoline (gboolean single_step, MonoTrampInfo **info, gbo
 
        return buf;
 }
-
-#if defined(ENABLE_GSHAREDVT) && defined(MONO_ARCH_GSHAREDVT_SUPPORTED)
-
-#include "../../../mono-extensions/mono/mini/tramp-amd64-gsharedvt.c"
-
-#else
-
-gpointer
-mono_amd64_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
-{
-       g_assert_not_reached ();
-       return NULL;
-}
-
-gpointer
-mono_arch_get_gsharedvt_arg_trampoline (MonoDomain *domain, gpointer arg, gpointer addr)
-{
-       g_assert_not_reached ();
-       return NULL;
-}
-
-gpointer
-mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
-{
-       *info = NULL;
-       return NULL;
-}
-
-#endif /* !ENABLE_GSHAREDVT */
diff --git a/mono/mini/tramp-arm-gsharedvt.c b/mono/mini/tramp-arm-gsharedvt.c
new file mode 100644 (file)
index 0000000..f84c542
--- /dev/null
@@ -0,0 +1,439 @@
+/*
+ * tramp-arm-gsharedvt.c: gsharedvt support code for arm
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <config.h>
+#include <glib.h>
+
+#include <mono/metadata/abi-details.h>
+#include <mono/metadata/appdomain.h>
+#include <mono/metadata/marshal.h>
+#include <mono/metadata/tabledefs.h>
+#include <mono/metadata/profiler-private.h>
+#include <mono/arch/arm/arm-codegen.h>
+#include <mono/arch/arm/arm-vfp-codegen.h>
+
+#include "mini.h"
+#include "mini-arm.h"
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+static inline guint8*
+emit_bx (guint8* code, int reg)
+{
+       if (mono_arm_thumb_supported ())
+               ARM_BX (code, reg);
+       else
+               ARM_MOV_REG_REG (code, ARMREG_PC, reg);
+       return code;
+}
+
+
+gpointer
+mono_arm_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       int i;
+
+       /*
+        * The caller/callee regs are mapped to slot 0..3, stack slot 0 is mapped to slot 4, etc.
+        */
+
+       /* Set vtype ret arg */
+       if (info->vret_slot != -1) {
+               callee [info->vret_arg_reg] = &callee [info->vret_slot];
+       }
+
+       for (i = 0; i < info->map_count; ++i) {
+               int src = info->map [i * 2];
+               int dst = info->map [(i * 2) + 1];
+               int arg_marshal = (src >> 16) & 0xff;
+
+               switch (arg_marshal) {
+               case GSHAREDVT_ARG_NONE:
+                       callee [dst] = caller [src];
+                       break;
+               case GSHAREDVT_ARG_BYVAL_TO_BYREF:
+                       /* gsharedvt argument passed by addr in reg/stack slot */
+                       src = src & 0xffff;
+                       callee [dst] = caller + src;
+                       break;
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL: {
+                       /* gsharedvt argument passed by value */
+                       int nslots = (src >> 4) & 0xff;
+                       int src_slot = src & 0xf;
+                       int j;
+                       gpointer *addr = caller [src_slot];
+
+                       for (j = 0; j < nslots; ++j)
+                               callee [dst + j] = addr [j];
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL_I1: {
+                       int src_slot = src & 0xf;
+                       gpointer *addr = caller [src_slot];
+
+                       callee [dst] = GINT_TO_POINTER ((int)*(gint8*)addr);
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL_I2: {
+                       int src_slot = src & 0xf;
+                       gpointer *addr = caller [src_slot];
+
+                       callee [dst] = GINT_TO_POINTER ((int)*(gint16*)addr);
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL_U1: {
+                       int src_slot = src & 0xf;
+                       gpointer *addr = caller [src_slot];
+
+                       callee [dst] = GUINT_TO_POINTER ((guint)*(guint8*)addr);
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL_U2: {
+                       int src_slot = src & 0xf;
+                       gpointer *addr = caller [src_slot];
+
+                       callee [dst] = GUINT_TO_POINTER ((guint)*(guint16*)addr);
+                       break;
+               }
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+       }
+
+       if (info->vcall_offset != -1) {
+               MonoObject *this_obj = caller [0];
+
+               if (G_UNLIKELY (!this_obj))
+                       return NULL;
+               if (info->vcall_offset == MONO_GSHAREDVT_DEL_INVOKE_VT_OFFSET)
+                       /* delegate invoke */
+                       return ((MonoDelegate*)this_obj)->invoke_impl;
+               else
+                       return *(gpointer*)((char*)this_obj->vtable + info->vcall_offset);
+       } else if (info->calli) {
+               /* The address to call is passed in the mrgctx reg */
+               return mrgctx_reg;
+       } else {
+               return info->addr;
+       }
+}
+
+#ifndef DISABLE_JIT
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int buf_len, cfa_offset;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+       guint8 *br_out, *br [16], *br_ret [16];
+       int i, arg_reg, npushed, info_offset, mrgctx_offset, caller_reg_area_offset, callee_reg_area_offset;
+       int lr_offset, fp, br_ret_index, args_size;
+
+       buf_len = 512;
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       arg_reg = ARMREG_R0;
+       /* Registers pushed by the arg trampoline */
+       npushed = 4;
+
+       // ios abi compatible frame
+       fp = ARMREG_R7;
+       cfa_offset = npushed * sizeof (gpointer);
+       mono_add_unwind_op_def_cfa (unwind_ops, code, buf, ARMREG_SP, cfa_offset);
+       ARM_PUSH (code, (1 << fp) | (1 << ARMREG_LR));
+       cfa_offset += 2 * sizeof (gpointer);
+       mono_add_unwind_op_def_cfa_offset (unwind_ops, code, buf, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, fp, (- cfa_offset));
+       mono_add_unwind_op_offset (unwind_ops, code, buf, ARMREG_LR, ((- cfa_offset) + 4));
+       ARM_MOV_REG_REG (code, fp, ARMREG_SP);
+       mono_add_unwind_op_def_cfa_reg (unwind_ops, code, buf, fp);
+       /* Allocate stack frame */
+       ARM_SUB_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, 32);
+       info_offset = -4;
+       mrgctx_offset = -8;
+       callee_reg_area_offset = - (6 * 4);
+       caller_reg_area_offset = cfa_offset - (npushed * sizeof (gpointer));
+       lr_offset = 4;
+       /* Save info struct which is in r0 */
+       ARM_STR_IMM (code, arg_reg, fp, info_offset);
+       /* Save rgctx reg */
+       ARM_STR_IMM (code, MONO_ARCH_RGCTX_REG, fp, mrgctx_offset);
+       /* Allocate callee area */
+       ARM_LDR_IMM (code, ARMREG_IP, arg_reg, MONO_STRUCT_OFFSET (GSharedVtCallInfo, stack_usage));
+       ARM_SUB_REG_REG (code, ARMREG_SP, ARMREG_SP, ARMREG_IP);
+       /* Allocate callee register area just below the callee area so it can be accessed from start_gsharedvt_call using negative offsets */
+       ARM_SUB_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, 4 * sizeof (gpointer));
+
+       /*
+        * The stack now looks like this:
+        * <caller frame>
+        * <saved r0-r3, lr>
+        * <saved fp> <- fp
+        * <our frame>
+        * <callee area> <- sp
+        */
+       g_assert (mono_arm_thumb_supported ());
+
+       /* Call start_gsharedvt_call () */
+       /* 4 arguments, needs 0 stack slot, need to clean it up after the call */
+       args_size = 0 * sizeof (gpointer);
+       ARM_SUB_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, args_size);
+       /* arg1 == info */
+       ARM_LDR_IMM (code, ARMREG_R0, fp, info_offset);
+       /* arg2 == caller stack area */
+       ARM_ADD_REG_IMM8 (code, ARMREG_R1, fp, cfa_offset - 4 * sizeof (gpointer));
+       /* arg3 == callee stack area */
+       ARM_ADD_REG_IMM8 (code, ARMREG_R2, ARMREG_SP, args_size);
+       /* arg4 == mrgctx reg */
+       ARM_LDR_IMM (code, ARMREG_R3, fp, mrgctx_offset);
+       /* Make the call */
+       if (aot) {
+               ji = mono_patch_info_list_prepend (ji, code - buf, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_arm_start_gsharedvt_call");
+               ARM_LDR_IMM (code, ARMREG_IP, ARMREG_PC, 0);
+               ARM_B (code, 0);
+               *(gpointer*)code = NULL;
+               code += 4;
+               ARM_LDR_REG_REG (code, ARMREG_IP, ARMREG_PC, ARMREG_IP);
+       } else {
+               ARM_LDR_IMM (code, ARMREG_IP, ARMREG_PC, 0);
+               ARM_B (code, 0);
+               *(gpointer*)code = mono_arm_start_gsharedvt_call;
+               code += 4;
+       }
+       ARM_MOV_REG_REG (code, ARMREG_LR, ARMREG_PC);
+       code = emit_bx (code, ARMREG_IP);
+       /* Clean up stack */
+       ARM_ADD_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, args_size);
+
+       /* Make the real method call */
+       /* R0 contains the addr to call */
+       ARM_MOV_REG_REG (code, ARMREG_IP, ARMREG_R0);
+       /* Load argument registers */
+       ARM_LDM (code, ARMREG_SP, (1 << ARMREG_R0) | (1 << ARMREG_R1) | (1 << ARMREG_R2) | (1 << ARMREG_R3));
+       /* Pop callee register area */
+       ARM_ADD_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, 4 * sizeof (gpointer));
+       /* Load rgctx */
+       ARM_LDR_IMM (code, MONO_ARCH_RGCTX_REG, fp, mrgctx_offset);
+       /* Make the call */
+#if 0
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, addr));
+#endif
+       /* mono_arch_find_imt_method () depends on this */
+       ARM_ADD_REG_IMM8 (code, ARMREG_LR, ARMREG_PC, 4);
+       ARM_BX (code, ARMREG_IP);
+       *((gpointer*)code) = NULL;
+       code += 4;
+
+       br_ret_index = 0;
+
+       /* Branch between IN/OUT cases */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, gsharedvt_in));
+
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, 1);
+       br_out = code;
+       ARM_B_COND (code, ARMCOND_NE, 0);
+
+       /* IN CASE */
+
+       /* LR == return marshalling type */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal));
+
+       /* Continue if no marshalling required */
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_NONE);
+       br_ret [br_ret_index ++] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+
+       /* Compute vret area address in LR */
+       ARM_LDR_IMM (code, ARMREG_LR, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_LR, ARMREG_LR, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_slot));
+       /* The slot value is off by 4 */
+       ARM_SUB_REG_IMM8 (code, ARMREG_LR, ARMREG_LR, 4);
+       ARM_SHL_IMM (code, ARMREG_LR, ARMREG_LR, 2);
+       ARM_ADD_REG_REG (code, ARMREG_LR, ARMREG_LR, ARMREG_SP);
+
+       /* Branch to specific marshalling code */
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_IREG);
+       br [0] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_IREGS);
+       br [1] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_I1);
+       br [2] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_U1);
+       br [3] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_I2);
+       br [4] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_U2);
+       br [5] = code;
+       ARM_B_COND (code, ARMCOND_EQ, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+
+       /* IN IREG case */
+       arm_patch (br [0], code);
+       ARM_LDR_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       /* IN IREGS case */
+       arm_patch (br [1], code);
+       ARM_LDR_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       ARM_LDR_IMM (code, ARMREG_R1, ARMREG_LR, 4);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       /* I1 case */
+       arm_patch (br [2], code);
+       ARM_LDRSB_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       /* U1 case */
+       arm_patch (br [3], code);
+       ARM_LDRB_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       /* I2 case */
+       arm_patch (br [4], code);
+       ARM_LDRSH_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       /* U2 case */
+       arm_patch (br [5], code);
+       ARM_LDRH_IMM (code, ARMREG_R0, ARMREG_LR, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+
+       /* OUT CASE */
+       arm_patch (br_out, code);
+
+       /* Marshal return value */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal));
+
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_IREGS);
+       br [0] = code;
+       ARM_B_COND (code, ARMCOND_NE, 0);
+
+       /* OUT IREGS case */
+       /* Load vtype ret addr from the caller arg regs */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_arg_reg));
+       ARM_SHL_IMM (code, ARMREG_IP, ARMREG_IP, 2);
+       ARM_ADD_REG_REG (code, ARMREG_IP, ARMREG_IP, fp);
+       ARM_ADD_REG_IMM8 (code, ARMREG_IP, ARMREG_IP, caller_reg_area_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, 0);
+       /* Save both registers for simplicity */
+       ARM_STR_IMM (code, ARMREG_R0, ARMREG_IP, 0);
+       ARM_STR_IMM (code, ARMREG_R1, ARMREG_IP, 4);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       arm_patch (br [0], code);
+
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_IREG);
+       br [0] = code;
+       ARM_B_COND (code, ARMCOND_NE, 0);
+
+       /* OUT IREG case */
+       /* Load vtype ret addr from the caller arg regs */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_arg_reg));
+       ARM_SHL_IMM (code, ARMREG_IP, ARMREG_IP, 2);
+       ARM_ADD_REG_REG (code, ARMREG_IP, ARMREG_IP, fp);
+       ARM_ADD_REG_IMM8 (code, ARMREG_IP, ARMREG_IP, caller_reg_area_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, 0);
+       /* Save the return value to the buffer pointed to by the vret addr */
+       ARM_STR_IMM (code, ARMREG_R0, ARMREG_IP, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       arm_patch (br [0], code);
+
+       ARM_CMP_REG_IMM8 (code, ARMREG_IP, GSHAREDVT_RET_U1);
+       br [0] = code;
+       ARM_B_COND (code, ARMCOND_NE, 0);
+
+       /* OUT U1 case */
+       /* Load vtype ret addr from the caller arg regs */
+       ARM_LDR_IMM (code, ARMREG_IP, fp, info_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_arg_reg));
+       ARM_SHL_IMM (code, ARMREG_IP, ARMREG_IP, 2);
+       ARM_ADD_REG_REG (code, ARMREG_IP, ARMREG_IP, fp);
+       ARM_ADD_REG_IMM8 (code, ARMREG_IP, ARMREG_IP, caller_reg_area_offset);
+       ARM_LDR_IMM (code, ARMREG_IP, ARMREG_IP, 0);
+       /* Save the return value to the buffer pointed to by the vret addr */
+       ARM_STRB_IMM (code, ARMREG_R0, ARMREG_IP, 0);
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+       arm_patch (br [0], code);
+
+       /* OUT other cases */
+       br_ret [br_ret_index ++] = code;
+       ARM_B (code, 0);
+
+       for (i = 0; i < br_ret_index; ++i)
+               arm_patch (br_ret [i], code);
+
+       /* Normal return */
+       /* Restore registers + stack */
+       ARM_MOV_REG_REG (code, ARMREG_SP, fp);
+       ARM_LDM (code, fp, (1 << fp) | (1 << ARMREG_LR));
+       ARM_ADD_REG_IMM8 (code, ARMREG_SP, ARMREG_SP, cfa_offset);
+       /* Return */
+       ARM_BX (code, ARMREG_LR);
+
+       g_assert ((code - buf) < buf_len);
+
+       if (info)
+               *info = mono_tramp_info_create ("gsharedvt_trampoline", buf, code - buf, ji, unwind_ops);
+
+       mono_arch_flush_icache (buf, code - buf);
+       return buf;
+}
+
+#else
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif
+
+
+#else
+
+
+gpointer
+mono_arm_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       *info = NULL;
+       return NULL;
+}
+
+
+#endif
index 2430e2295ceda8979dab5340ee18e038b737c70b..5ff7bbfdfc8309b5105e0052c8b39dc1199e92b4 100644 (file)
@@ -7,6 +7,7 @@
  * (C) 2001-2003 Ximian, Inc.
  * Copyright 2003-2011 Novell Inc
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -910,7 +911,7 @@ mono_arch_create_sdb_trampoline (gboolean single_step, MonoTrampInfo **info, gbo
        ARM_STR_IMM (code, ARMREG_R0, ARMREG_FP, MONO_STRUCT_OFFSET (MonoContext, regs) + 4 * ARMREG_SP);
 
        /* make ctx.eip hold the address of the call. */
-       ARM_SUB_REG_IMM8 (code, ARMREG_LR, ARMREG_LR, 4);
+       //ARM_SUB_REG_IMM8 (code, ARMREG_LR, ARMREG_LR, 4);
        ARM_STR_IMM (code, ARMREG_LR, ARMREG_FP, MONO_STRUCT_OFFSET (MonoContext, pc));
 
        /* r0 now points to the MonoContext */
@@ -1134,25 +1135,3 @@ mono_arch_get_gsharedvt_arg_trampoline (MonoDomain *domain, gpointer arg, gpoint
 }
 
 #endif
-
-#if defined(ENABLE_GSHAREDVT)
-
-#include "../../../mono-extensions/mono/mini/tramp-arm-gsharedvt.c"
-
-#else
-
-gpointer
-mono_arm_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
-{
-       g_assert_not_reached ();
-       return NULL;
-}
-
-gpointer
-mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
-{
-       *info = NULL;
-       return NULL;
-}
-
-#endif /* !MONOTOUCH */
diff --git a/mono/mini/tramp-arm64-gsharedvt.c b/mono/mini/tramp-arm64-gsharedvt.c
new file mode 100644 (file)
index 0000000..175f75d
--- /dev/null
@@ -0,0 +1,565 @@
+/*
+ * tramp-arm64-gsharedvt.c: gsharedvt support code for arm64
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include <mono/metadata/abi-details.h>
+
+#include "mini.h"
+#include "mini-arm64.h"
+#include "mini-arm64-gsharedvt.h"
+
+/*
+ * GSHAREDVT
+ */
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+/*
+ * mono_arch_get_gsharedvt_arg_trampoline:
+ *
+ *   See tramp-x86.c for documentation.
+ */
+gpointer
+mono_arch_get_gsharedvt_arg_trampoline (MonoDomain *domain, gpointer arg, gpointer addr)
+{
+       guint8 *code, *buf;
+       int buf_len = 40;
+
+       /*
+        * Return a trampoline which calls ADDR passing in ARG.
+        * Pass the argument in ip1, clobbering ip0.
+        */
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       code = mono_arm_emit_imm64 (code, ARMREG_IP1, (guint64)arg);
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)addr);
+
+       arm_brx (code, ARMREG_IP0);
+
+       g_assert ((code - buf) < buf_len);
+       mono_arch_flush_icache (buf, code - buf);
+
+       return buf;
+}
+
+gpointer
+mono_arm_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       int i;
+
+       /* Set vtype ret arg */
+       if (info->vret_slot != -1) {
+               g_assert (info->vret_slot);
+               callee [info->vret_arg_reg] = &callee [info->vret_slot];
+       }
+
+       for (i = 0; i < info->map_count; ++i) {
+               int src = info->map [i * 2];
+               int dst = info->map [(i * 2) + 1];
+               int arg_marshal = (src >> 18) & 0xf;
+               int arg_size = (src >> 22) & 0xf;
+
+               if (G_UNLIKELY (arg_size)) {
+                       int src_offset = (src >> 26) & 0xf;
+                       int dst_offset = (dst >> 26) & 0xf;
+                       int src_slot, dst_slot;
+                       guint8 *src_ptr, *dst_ptr;
+
+                       /*
+                        * Argument passed in part of a stack slot on ios.
+                        * src_offset/dst_offset is the offset within the stack slot.
+                        */
+                       switch (arg_marshal) {
+                       case GSHAREDVT_ARG_NONE:
+                               src_slot = src & 0xffff;
+                               dst_slot = dst & 0xffff;
+                               src_ptr = (guint8*)(caller + src_slot) + src_offset;
+                               dst_ptr = (guint8*)(callee + dst_slot) + dst_offset;
+                               break;
+                       case GSHAREDVT_ARG_BYREF_TO_BYVAL:
+                               src_slot = src & 0x3f;
+                               dst_slot = dst & 0xffff;
+                               src_ptr = caller [src_slot];
+                               dst_ptr = (guint8*)(callee + dst_slot) + dst_offset;
+                               break;
+                       case GSHAREDVT_ARG_BYVAL_TO_BYREF_HFAR4:
+                       case GSHAREDVT_ARG_BYREF_TO_BYVAL_HFAR4:
+                       case GSHAREDVT_ARG_BYREF_TO_BYREF:
+                               g_assert_not_reached ();
+                               break;
+                       case GSHAREDVT_ARG_BYVAL_TO_BYREF:
+                               src_slot = src & 0x3f;
+                               src_ptr = caller + src_slot + src_offset;
+                               callee [dst] = src_ptr;
+                               break;
+                       default:
+                               NOT_IMPLEMENTED;
+                               break;
+                       }
+
+                       if (arg_marshal == GSHAREDVT_ARG_BYVAL_TO_BYREF)
+                               continue;
+
+                       switch (arg_size) {
+                       case GSHAREDVT_ARG_SIZE_I1:
+                               *(gint8*)dst_ptr = *(gint8*)src_ptr;
+                               break;
+                       case GSHAREDVT_ARG_SIZE_U1:
+                               *(guint8*)dst_ptr = *(guint8*)src_ptr;
+                               break;
+                       case GSHAREDVT_ARG_SIZE_I2:
+                               *(gint16*)dst_ptr = *(gint16*)src_ptr;
+                               break;
+                       case GSHAREDVT_ARG_SIZE_U2:
+                               *(guint16*)dst_ptr = *(guint16*)src_ptr;
+                               break;
+                       case GSHAREDVT_ARG_SIZE_I4:
+                               *(gint32*)dst_ptr = *(gint32*)src_ptr;
+                               break;
+                       case GSHAREDVT_ARG_SIZE_U4:
+                               *(guint32*)dst_ptr = *(guint32*)src_ptr;
+                               break;
+                       default:
+                               g_assert_not_reached ();
+                       }
+                       continue;
+               }
+
+               switch (arg_marshal) {
+               case GSHAREDVT_ARG_NONE:
+                       callee [dst] = caller [src];
+                       break;
+               case GSHAREDVT_ARG_BYVAL_TO_BYREF:
+                       /* gsharedvt argument passed by addr in reg/stack slot */
+                       src = src & 0x3f;
+                       callee [dst] = caller + src;
+                       break;
+               case GSHAREDVT_ARG_BYVAL_TO_BYREF_HFAR4: {
+                       int nslots = (src >> 6) & 0xff;
+                       int src_slot = src & 0x3f;
+                       int j;
+                       float *dst_arr = (float*)(caller + src_slot);
+
+                       /* The r4 hfa is in separate slots, need to compress them together in place */
+                       for (j = 0; j < nslots; ++j)
+                               dst_arr [j] = *(float*)(caller + src_slot + j);
+
+                       callee [dst] = caller + src_slot;
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL: {
+                       int nslots = (src >> 6) & 0xff;
+                       int src_slot = src & 0x3f;
+                       int j;
+                       gpointer *addr = caller [src_slot];
+
+                       for (j = 0; j < nslots; ++j)
+                               callee [dst + j] = addr [j];
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYVAL_HFAR4: {
+                       int nslots = (src >> 6) & 0xff;
+                       int src_slot = src & 0x3f;
+                       int j;
+                       guint32 *addr = (guint32*)(caller [src_slot]);
+
+                       /* addr points to an array of floats, need to load them to registers */
+                       for (j = 0; j < nslots; ++j)
+                               callee [dst + j] = GUINT_TO_POINTER (addr [j]);
+                       break;
+               }
+               case GSHAREDVT_ARG_BYREF_TO_BYREF: {
+                       int src_slot = src & 0x3f;
+
+                       callee [dst] = caller [src_slot];
+                       break;
+               }
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+       }
+
+       if (info->vcall_offset != -1) {
+               MonoObject *this_obj = caller [0];
+
+               if (G_UNLIKELY (!this_obj))
+                       return NULL;
+               if (info->vcall_offset == MONO_GSHAREDVT_DEL_INVOKE_VT_OFFSET)
+                       /* delegate invoke */
+                       return ((MonoDelegate*)this_obj)->invoke_impl;
+               else
+                       return *(gpointer*)((char*)this_obj->vtable + info->vcall_offset);
+       } else if (info->calli) {
+               /* The address to call is passed in the mrgctx reg */
+               return mrgctx_reg;
+       } else {
+               return info->addr;
+       }
+}
+
+#ifndef DISABLE_JIT
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int buf_len, cfa_offset;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+       guint8 *br_out, *br [64], *br_ret [64], *bcc_ret [64];
+       int i, n_arg_regs, n_arg_fregs, offset, arg_reg, info_offset, rgctx_arg_reg_offset;
+       int caller_reg_area_offset, callee_reg_area_offset, callee_stack_area_offset;
+       int br_ret_index, bcc_ret_index;
+
+       buf_len = 2048;
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       /*
+        * We are being called by an gsharedvt arg trampoline, the info argument is in IP1.
+        */
+       arg_reg = ARMREG_IP1;
+       n_arg_regs = NUM_GSHAREDVT_ARG_GREGS;
+       n_arg_fregs = NUM_GSHAREDVT_ARG_FREGS;
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* frame block */
+       offset += 2 * 8;
+       /* info argument */
+       info_offset = offset;
+       offset += 8;
+       /* saved rgctx */
+       rgctx_arg_reg_offset = offset;
+       offset += 8;
+       /* alignment */
+       offset += 8;
+       /* argument regs */
+       caller_reg_area_offset = offset;
+       offset += (n_arg_regs + n_arg_fregs) * 8;
+
+       /* We need the argument regs to be saved at the top of the frame */
+       g_assert (offset % MONO_ARCH_FRAME_ALIGNMENT == 0);
+
+       cfa_offset = offset;
+
+       /* Setup frame */
+       arm_stpx_pre (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, -cfa_offset);
+       mono_add_unwind_op_def_cfa (unwind_ops, code, buf, ARMREG_SP, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, ARMREG_FP, -cfa_offset + 0);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, ARMREG_LR, -cfa_offset + 8);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+       mono_add_unwind_op_def_cfa_reg (unwind_ops, code, buf, ARMREG_FP);
+
+       /* Save info argument */
+       arm_strx (code, arg_reg, ARMREG_FP, info_offset);
+
+       /* Save rgxctx */
+       arm_strx (code, MONO_ARCH_RGCTX_REG, ARMREG_FP, rgctx_arg_reg_offset);
+
+       /* Save argument regs below the stack arguments */
+       for (i = 0; i < n_arg_regs; ++i)
+               arm_strx (code, i, ARMREG_SP, caller_reg_area_offset + (i * 8));
+       // FIXME: Only do this if fp regs are used
+       for (i = 0; i < n_arg_fregs; ++i)
+               arm_strfpx (code, i, ARMREG_SP, caller_reg_area_offset + ((n_arg_regs + i) * 8));
+
+       /* Allocate callee area */
+       arm_ldrw (code, ARMREG_IP0, arg_reg, MONO_STRUCT_OFFSET (GSharedVtCallInfo, stack_usage));
+       arm_movspx (code, ARMREG_LR, ARMREG_SP);
+       arm_subx (code, ARMREG_LR, ARMREG_LR, ARMREG_IP0);
+       arm_movspx (code, ARMREG_SP, ARMREG_LR);
+       /* Allocate callee register area just below the callee area so it can be accessed from start_gsharedvt_call using negative offsets */
+       /* The + 8 is for alignment */
+       callee_reg_area_offset = 8;
+       callee_stack_area_offset = callee_reg_area_offset + (n_arg_regs * sizeof (gpointer));
+       arm_subx_imm (code, ARMREG_SP, ARMREG_SP, ((n_arg_regs + n_arg_fregs) * sizeof (gpointer)) + 8);
+
+       /*
+        * The stack now looks like this:
+        * <caller frame>
+        * <saved r0-r8>
+        * <our frame>
+        * <saved fp, lr> <- fp
+        * <callee area> <- sp
+        */
+
+       /* Call start_gsharedvt_call () */
+       /* arg1 == info */
+       arm_ldrx (code, ARMREG_R0, ARMREG_FP, info_offset);
+       /* arg2 = caller stack area */
+       arm_addx_imm (code, ARMREG_R1, ARMREG_FP, caller_reg_area_offset);
+       /* arg3 == callee stack area */
+       arm_addx_imm (code, ARMREG_R2, ARMREG_SP, callee_reg_area_offset);
+       /* arg4 = mrgctx reg */
+       arm_ldrx (code, ARMREG_R3, ARMREG_FP, rgctx_arg_reg_offset);
+
+       if (aot)
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_arm_start_gsharedvt_call");
+       else
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)mono_arm_start_gsharedvt_call);
+       arm_blrx (code, ARMREG_IP0);
+
+       /* Make the real method call */
+       /* R0 contains the addr to call */
+       arm_movx (code, ARMREG_IP1, ARMREG_R0);
+       /* Load rgxctx */
+       arm_ldrx (code, MONO_ARCH_RGCTX_REG, ARMREG_FP, rgctx_arg_reg_offset);
+       /* Load argument registers */
+       // FIXME:
+       for (i = 0; i < n_arg_regs; ++i)
+               arm_ldrx (code, i, ARMREG_SP, callee_reg_area_offset + (i * 8));
+       // FIXME: Only do this if needed
+       for (i = 0; i < n_arg_fregs; ++i)
+               arm_ldrfpx (code, i, ARMREG_SP, callee_reg_area_offset + ((n_arg_regs + i) * 8));
+       /* Clear callee reg area */
+       arm_addx_imm (code, ARMREG_SP, ARMREG_SP, ((n_arg_regs + n_arg_fregs) * sizeof (gpointer)) + 8);
+       /* Make the call */
+       arm_blrx (code, ARMREG_IP1);
+
+       br_ret_index = 0;
+       bcc_ret_index = 0;
+
+       // FIXME: Use a switch
+       /* Branch between IN/OUT cases */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, info_offset);
+       arm_ldrw (code, ARMREG_IP1, ARMREG_IP1, MONO_STRUCT_OFFSET (GSharedVtCallInfo, gsharedvt_in));
+       br_out = code;
+       arm_cbzx (code, ARMREG_IP1, 0);
+
+       /* IN CASE */
+
+       /* IP1 == return marshalling type */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, info_offset);
+       arm_ldrw (code, ARMREG_IP1, ARMREG_IP1, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal));
+
+       /* Continue if no marshalling required */
+       // FIXME: Use cmpx_imm
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, GSHAREDVT_RET_NONE);
+       arm_cmpx (code, ARMREG_IP0, ARMREG_IP1);
+       bcc_ret [bcc_ret_index ++] = code;
+       arm_bcc (code, ARMCOND_EQ, 0);
+
+       /* Compute vret area address in LR */
+       arm_ldrx (code, ARMREG_LR, ARMREG_FP, info_offset);
+       arm_ldrw (code, ARMREG_LR, ARMREG_LR, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_slot));
+       arm_subx_imm (code, ARMREG_LR, ARMREG_LR, n_arg_regs + n_arg_fregs);
+       arm_lslx (code, ARMREG_LR, ARMREG_LR, 3);
+       arm_movspx (code, ARMREG_IP0, ARMREG_SP);
+       arm_addx (code, ARMREG_LR, ARMREG_IP0, ARMREG_LR);
+
+       /* Branch to specific marshalling code */
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, i);
+               arm_cmpx (code, ARMREG_IP0, ARMREG_IP1);
+               br [i] = code;
+               arm_bcc (code, ARMCOND_EQ, 0);
+       }
+
+       arm_brk (code, 0);
+
+       /*
+        * The address of the return value area is in LR, have to load it into
+        * registers.
+        */
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               mono_arm_patch (br [i], code, MONO_R_ARM64_BCC);
+               switch (i) {
+               case GSHAREDVT_RET_NONE:
+                       break;
+               case GSHAREDVT_RET_I8:
+                       arm_ldrx (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I1:
+                       arm_ldrsbx (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_U1:
+                       arm_ldrb (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I2:
+                       arm_ldrshx (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_U2:
+                       arm_ldrh (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I4:
+                       arm_ldrswx (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_U4:
+                       arm_ldrw (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_R8:
+                       arm_ldrfpx (code, ARMREG_D0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_R4:
+                       arm_ldrfpw (code, ARMREG_D0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_IREGS_1:
+               case GSHAREDVT_RET_IREGS_2:
+               case GSHAREDVT_RET_IREGS_3:
+               case GSHAREDVT_RET_IREGS_4:
+               case GSHAREDVT_RET_IREGS_5:
+               case GSHAREDVT_RET_IREGS_6:
+               case GSHAREDVT_RET_IREGS_7:
+               case GSHAREDVT_RET_IREGS_8: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_IREGS_1 + 1; ++j)
+                               arm_ldrx (code, j, ARMREG_LR, j * 8);
+                       break;
+               }
+               case GSHAREDVT_RET_HFAR8_1:
+               case GSHAREDVT_RET_HFAR8_2:
+               case GSHAREDVT_RET_HFAR8_3:
+               case GSHAREDVT_RET_HFAR8_4: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_HFAR8_1 + 1; ++j)
+                               arm_ldrfpx (code, j, ARMREG_LR, j * 8);
+                       break;
+               }
+               case GSHAREDVT_RET_HFAR4_1:
+               case GSHAREDVT_RET_HFAR4_2:
+               case GSHAREDVT_RET_HFAR4_3:
+               case GSHAREDVT_RET_HFAR4_4: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_HFAR4_1 + 1; ++j)
+                               arm_ldrfpw (code, j, ARMREG_LR, j * 4);
+                       break;
+               }
+               default:
+                       g_assert_not_reached ();
+                       break;
+               }
+               br_ret [br_ret_index ++] = code;
+               arm_b (code, 0);
+       }
+
+       /* OUT CASE */
+       mono_arm_patch (br_out, code, MONO_R_ARM64_CBZ);
+
+       /* Compute vret area address in LR */
+       arm_ldrx (code, ARMREG_LR, ARMREG_FP, caller_reg_area_offset + (ARMREG_R8 * 8));
+
+       /* IP1 == return marshalling type */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, info_offset);
+       arm_ldrw (code, ARMREG_IP1, ARMREG_IP1, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal));
+
+       /* Branch to specific marshalling code */
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, i);
+               arm_cmpx (code, ARMREG_IP0, ARMREG_IP1);
+               br [i] = code;
+               arm_bcc (code, ARMCOND_EQ, 0);
+       }
+
+       /*
+        * The return value is in registers, need to save to the return area passed by the caller in
+        * R8.
+        */
+       for (i = GSHAREDVT_RET_NONE; i < GSHAREDVT_RET_NUM; ++i) {
+               mono_arm_patch (br [i], code, MONO_R_ARM64_BCC);
+               switch (i) {
+               case GSHAREDVT_RET_NONE:
+                       break;
+               case GSHAREDVT_RET_I8:
+                       arm_strx (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I1:
+               case GSHAREDVT_RET_U1:
+                       arm_strb (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I2:
+               case GSHAREDVT_RET_U2:
+                       arm_strh (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_I4:
+               case GSHAREDVT_RET_U4:
+                       arm_strw (code, ARMREG_R0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_R8:
+                       arm_strfpx (code, ARMREG_D0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_R4:
+                       arm_strfpw (code, ARMREG_D0, ARMREG_LR, 0);
+                       break;
+               case GSHAREDVT_RET_IREGS_1:
+               case GSHAREDVT_RET_IREGS_2:
+               case GSHAREDVT_RET_IREGS_3:
+               case GSHAREDVT_RET_IREGS_4:
+               case GSHAREDVT_RET_IREGS_5:
+               case GSHAREDVT_RET_IREGS_6:
+               case GSHAREDVT_RET_IREGS_7:
+               case GSHAREDVT_RET_IREGS_8: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_IREGS_1 + 1; ++j)
+                               arm_strx (code, j, ARMREG_LR, j * 8);
+                       break;
+               }
+               case GSHAREDVT_RET_HFAR8_1:
+               case GSHAREDVT_RET_HFAR8_2:
+               case GSHAREDVT_RET_HFAR8_3:
+               case GSHAREDVT_RET_HFAR8_4: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_HFAR8_1 + 1; ++j)
+                               arm_strfpx (code, j, ARMREG_LR, j * 8);
+                       break;
+               }
+               case GSHAREDVT_RET_HFAR4_1:
+               case GSHAREDVT_RET_HFAR4_2:
+               case GSHAREDVT_RET_HFAR4_3:
+               case GSHAREDVT_RET_HFAR4_4: {
+                       int j;
+
+                       for (j = 0; j < i - GSHAREDVT_RET_HFAR4_1 + 1; ++j)
+                               arm_strfpw (code, j, ARMREG_LR, j * 4);
+                       break;
+               }
+               default:
+                       arm_brk (code, i);
+                       break;
+               }
+               br_ret [br_ret_index ++] = code;
+               arm_b (code, 0);
+       }
+
+       arm_brk (code, 0);
+
+       for (i = 0; i < br_ret_index; ++i)
+               mono_arm_patch (br_ret [i], code, MONO_R_ARM64_B);
+       for (i = 0; i < bcc_ret_index; ++i)
+               mono_arm_patch (bcc_ret [i], code, MONO_R_ARM64_BCC);
+
+       /* Normal return */
+       arm_movspx (code, ARMREG_SP, ARMREG_FP);
+       arm_ldpx_post (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, offset);
+       arm_retx (code, ARMREG_LR);
+
+       g_assert ((code - buf) < buf_len);
+
+       if (info)
+               *info = mono_tramp_info_create ("gsharedvt_trampoline", buf, code - buf, ji, unwind_ops);
+
+       mono_arch_flush_icache (buf, code - buf);
+       return buf;
+}
+
+#else
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif
+
+#endif /* MONO_ARCH_GSHAREDVT_SUPPORTED */
index 16504375d849259e6969308533fcf70d29245161..4bd7ac33474b3f31f592213448c9774f3f3cbfe5 100644 (file)
@@ -1 +1,714 @@
-#include "../../../mono-extensions/mono/mini/tramp-arm64.c"
+/*
+ * tramp-arm64.c: JIT trampoline code for ARM64
+ *
+ * Copyright 2013 Xamarin Inc
+ *
+ * Based on tramp-arm.c:
+ * 
+ * Authors:
+ *   Paolo Molaro (lupus@ximian.com)
+ *
+ * (C) 2001-2003 Ximian, Inc.
+ * Copyright 2003-2011 Novell Inc
+ * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+
+#include "mini.h"
+#include "debugger-agent.h"
+
+#include <mono/arch/arm64/arm64-codegen.h>
+#include <mono/metadata/abi-details.h>
+
+#define ALIGN_TO(val,align) ((((guint64)val) + ((align) - 1)) & ~((align) - 1))
+
+void
+mono_arch_patch_callsite (guint8 *method_start, guint8 *code_ptr, guint8 *addr)
+{
+       mono_arm_patch (code_ptr - 4, addr, MONO_R_ARM64_BL);
+       mono_arch_flush_icache (code_ptr - 4, 4);
+}
+
+void
+mono_arch_patch_plt_entry (guint8 *code, gpointer *got, mgreg_t *regs, guint8 *addr)
+{
+       guint32 ins;
+       guint64 slot_addr;
+       int disp;
+
+       /* 
+        * Decode the address loaded by the PLT entry emitted by arch_emit_plt_entry () in
+        * aot-compiler.c
+        */
+
+       /* adrp */
+       ins = ((guint32*)code) [0];
+       g_assert (((ins >> 24) & 0x1f) == 0x10);
+       disp = (((ins >> 5) & 0x7ffff) << 2) | ((ins >> 29) & 0x3);
+       /* FIXME: disp is signed */
+       g_assert ((disp >> 20) == 0);
+
+       slot_addr = ((guint64)code + (disp << 12)) & ~0xfff;
+
+       /* add x16, x16, :lo12:got */
+       ins = ((guint32*)code) [1];
+       g_assert (((ins >> 22) & 0x3) == 0);
+       slot_addr += (ins >> 10) & 0xfff;
+
+       /* ldr x16, [x16, <offset>] */
+       ins = ((guint32*)code) [2];
+       g_assert (((ins >> 24) & 0x3f) == 0x39);
+       slot_addr += ((ins >> 10) & 0xfff) * 8;
+
+       g_assert (*(guint64*)slot_addr);
+       *(gpointer*)slot_addr = addr;
+}
+
+guint8*
+mono_arch_get_call_target (guint8 *code)
+{
+       guint32 imm;
+       int disp;
+
+       code -= 4;
+
+       imm = *(guint32*)code;
+       /* Should be a bl */
+       g_assert (((imm >> 31) & 0x1) == 0x1);
+       g_assert (((imm >> 26) & 0x7) == 0x5);
+
+       disp = (imm & 0x3ffffff);
+       if ((disp >> 25) != 0)
+               /* Negative, sing extend to 32 bits */
+               disp = disp | 0xfc000000;
+
+       return code + (disp * 4);
+}
+
+guint32
+mono_arch_get_plt_info_offset (guint8 *plt_entry, mgreg_t *regs, guint8 *code)
+{
+       /* The offset is stored as the 5th word of the plt entry */
+       return ((guint32*)plt_entry) [4];
+}
+
+#ifndef DISABLE_JIT
+
+guchar*
+mono_arch_create_generic_trampoline (MonoTrampolineType tramp_type, MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf, *tramp, *labels [16];
+       int i, buf_len, imm;
+       int frame_size, offset, gregs_offset, num_fregs, fregs_offset, arg_offset, lmf_offset, res_offset;
+       guint64 gregs_regset;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+       char *tramp_name;
+
+       buf_len = 768;
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       /*
+        * We are getting called by a specific trampoline, ip1 contains the trampoline argument.
+        */
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* frame block */
+       offset += 2 * 8;
+       /* gregs */
+       gregs_offset = offset;
+       offset += 32 * 8;
+       /* fregs */
+       // FIXME: Save 128 bits
+       /* Only have to save the argument regs */
+       num_fregs = 8;
+       fregs_offset = offset;
+       offset += num_fregs * 8;
+       /* arg */
+       arg_offset = offset;
+       offset += 8;
+       /* result */
+       res_offset = offset;
+       offset += 8;
+       /* LMF */
+       lmf_offset = offset;
+       offset += sizeof (MonoLMF);
+       //offset += 22 * 8;
+       frame_size = ALIGN_TO (offset, MONO_ARCH_FRAME_ALIGNMENT);
+
+       /* Setup stack frame */
+       imm = frame_size;
+       while (imm > 256) {
+               arm_subx_imm (code, ARMREG_SP, ARMREG_SP, 256);
+               imm -= 256;
+       }
+       arm_subx_imm (code, ARMREG_SP, ARMREG_SP, imm);
+       arm_stpx (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, 0);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+
+       /* Save gregs */
+       // FIXME: Optimize this
+       gregs_regset = ~((1 << ARMREG_FP) | (1 << ARMREG_SP));
+       code = mono_arm_emit_store_regarray (code, gregs_regset, ARMREG_FP, gregs_offset);
+       /* Save fregs */
+       for (i = 0; i < num_fregs; ++i)
+               arm_strfpx (code, i, ARMREG_FP, fregs_offset + (i * 8));
+       /* Save trampoline arg */
+       arm_strx (code, ARMREG_IP1, ARMREG_FP, arg_offset);
+
+       /* Setup LMF */
+       arm_addx_imm (code, ARMREG_IP0, ARMREG_FP, lmf_offset);
+       code = mono_arm_emit_store_regset (code, MONO_ARCH_LMF_REGS, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, gregs));
+       /* Save caller fp */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, 0);
+       arm_strx (code, ARMREG_IP1, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, gregs) + (MONO_ARCH_LMF_REG_FP * 8));
+       /* Save caller sp */
+       arm_movx (code, ARMREG_IP1, ARMREG_FP);
+       imm = frame_size;
+       while (imm > 256) {
+               arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, 256);
+               imm -= 256;
+       }
+       arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, imm);
+       arm_strx (code, ARMREG_IP1, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, gregs) + (MONO_ARCH_LMF_REG_SP * 8));
+       /* Save caller pc */
+       if (tramp_type == MONO_TRAMPOLINE_JUMP)
+               arm_movx (code, ARMREG_LR, ARMREG_RZR);
+       else
+               arm_ldrx (code, ARMREG_LR, ARMREG_FP, 8);
+       arm_strx (code, ARMREG_LR, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, pc));
+
+       /* Save LMF */
+       /* Similar to emit_save_lmf () */
+       if (aot) {
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_get_lmf_addr");
+       } else {
+               tramp = (guint8*)mono_get_lmf_addr;
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)tramp);
+       }
+       arm_blrx (code, ARMREG_IP0);
+       /* r0 contains the address of the tls slot holding the current lmf */
+       /* ip0 = lmf */
+       arm_addx_imm (code, ARMREG_IP0, ARMREG_FP, lmf_offset);
+       /* lmf->lmf_addr = lmf_addr */
+       arm_strx (code, ARMREG_R0, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, lmf_addr));
+       /* lmf->previous_lmf = *lmf_addr */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_R0, 0);
+       arm_strx (code, ARMREG_IP1, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, previous_lmf));
+       /* *lmf_addr = lmf */
+       arm_strx (code, ARMREG_IP0, ARMREG_R0, 0);
+
+       /* Call the C trampoline function */
+       /* Arg 1 = gregs */
+       arm_addx_imm (code, ARMREG_R0, ARMREG_FP, gregs_offset);
+       /* Arg 2 = caller */
+       if (tramp_type == MONO_TRAMPOLINE_JUMP)
+               arm_movx (code, ARMREG_R1, ARMREG_RZR);
+       else
+               arm_ldrx (code, ARMREG_R1, ARMREG_FP, gregs_offset + (ARMREG_LR * 8));
+       /* Arg 3 = arg */
+       if (MONO_TRAMPOLINE_TYPE_HAS_ARG (tramp_type))
+               /* Passed in r0 */
+               arm_ldrx (code, ARMREG_R2, ARMREG_FP, gregs_offset + (ARMREG_R0 * 8));
+       else
+               arm_ldrx (code, ARMREG_R2, ARMREG_FP, arg_offset);
+       /* Arg 4 = trampoline addr */
+       arm_movx (code, ARMREG_R3, ARMREG_RZR);
+
+       if (aot) {
+               char *icall_name = g_strdup_printf ("trampoline_func_%d", tramp_type);
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, icall_name);
+       } else {
+               tramp = (guint8*)mono_get_trampoline_func (tramp_type);
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)tramp);
+       }
+       arm_blrx (code, ARMREG_IP0);
+
+       /* Save the result */
+       arm_strx (code, ARMREG_R0, ARMREG_FP, res_offset);
+
+       /* Restore LMF */
+       /* Similar to emit_restore_lmf () */
+       /* Clobbers ip0/ip1 */
+       /* ip0 = lmf */
+       arm_addx_imm (code, ARMREG_IP0, ARMREG_FP, lmf_offset);
+       /* ip1 = lmf->previous_lmf */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, previous_lmf));
+       /* ip0 = lmf->lmf_addr */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, MONO_STRUCT_OFFSET (MonoLMF, lmf_addr));
+       /* *lmf_addr = previous_lmf */
+       arm_strx (code, ARMREG_IP1, ARMREG_IP0, 0);
+
+       /* Check for thread interruption */
+       /* This is not perf critical code so no need to check the interrupt flag */
+       if (aot) {
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_thread_force_interruption_checkpoint_noraise");
+       } else {
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)mono_thread_force_interruption_checkpoint_noraise);
+       }
+       arm_blrx (code, ARMREG_IP0);
+       /* Check whenever there is an exception to be thrown */
+       labels [0] = code;
+       arm_cbnzx (code, ARMREG_R0, 0);
+
+       /* Normal case */
+
+       /* Restore gregs */
+       /* Only have to load the argument regs (r0..r8) and the rgctx reg */
+       code = mono_arm_emit_load_regarray (code, 0x1ff | (1 << ARMREG_LR) | (1 << MONO_ARCH_RGCTX_REG), ARMREG_FP, gregs_offset);
+       /* Restore fregs */
+       for (i = 0; i < num_fregs; ++i)
+               arm_ldrfpx (code, i, ARMREG_FP, fregs_offset + (i * 8));
+
+       /* Load the result */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, res_offset);
+
+       /* These trampolines return a value */
+       if (tramp_type == MONO_TRAMPOLINE_RGCTX_LAZY_FETCH)
+               arm_movx (code, ARMREG_R0, ARMREG_IP1);
+
+       /* Cleanup frame */
+       code = mono_arm_emit_destroy_frame (code, frame_size, ((1 << ARMREG_IP0)));
+
+       if (tramp_type == MONO_TRAMPOLINE_RGCTX_LAZY_FETCH)
+               arm_retx (code, ARMREG_LR);
+       else
+               arm_brx (code, ARMREG_IP1);
+
+       /* Exception case */
+       mono_arm_patch (labels [0], code, MONO_R_ARM64_CBZ);
+
+       /*
+        * We have an exception we want to throw in the caller's frame, so pop
+        * the trampoline frame and throw from the caller.
+        */
+       code = mono_arm_emit_destroy_frame (code, frame_size, ((1 << ARMREG_IP0)));
+       /* We are in the parent frame, the exception is in x0 */
+       /*
+        * EH is initialized after trampolines, so get the address of the variable
+        * which contains throw_exception, and load it from there.
+        */
+       if (aot) {
+               /* Not really a jit icall */
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "throw_exception_addr");
+       } else {
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)mono_get_throw_exception_addr ());
+       }
+       arm_ldrx (code, ARMREG_IP0, ARMREG_IP0, 0);
+       /* lr contains the return address, the trampoline will use it as the throw site */
+       arm_brx (code, ARMREG_IP0);
+
+       g_assert ((code - buf) < buf_len);
+       mono_arch_flush_icache (buf, code - buf);
+
+       if (info) {
+               tramp_name = mono_get_generic_trampoline_name (tramp_type);
+               *info = mono_tramp_info_create (tramp_name, buf, code - buf, ji, unwind_ops);
+               g_free (tramp_name);
+       }
+
+       return buf;
+}
+
+gpointer
+mono_arch_create_specific_trampoline (gpointer arg1, MonoTrampolineType tramp_type, MonoDomain *domain, guint32 *code_len)
+{
+       guint8 *code, *buf, *tramp;
+       int buf_len = 64;
+
+       /*
+        * Return a trampoline which calls generic trampoline TRAMP_TYPE passing in ARG1.
+        * Pass the argument in ip1, clobbering ip0.
+        */
+       tramp = mono_get_trampoline_code (tramp_type);
+
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       code = mono_arm_emit_imm64 (code, ARMREG_IP1, (guint64)arg1);
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)tramp);
+
+       arm_brx (code, ARMREG_IP0);
+
+       g_assert ((code - buf) < buf_len);
+       mono_arch_flush_icache (buf, code - buf);
+       if (code_len)
+               *code_len = code - buf;
+
+       return buf;
+}
+
+gpointer
+mono_arch_get_unbox_trampoline (MonoMethod *m, gpointer addr)
+{
+       guint8 *code, *start;
+       guint32 size = 32;
+       MonoDomain *domain = mono_domain_get ();
+
+       start = code = mono_domain_code_reserve (domain, size);
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)addr);
+       arm_addx_imm (code, ARMREG_R0, ARMREG_R0, sizeof (MonoObject));
+       arm_brx (code, ARMREG_IP0);
+
+       g_assert ((code - start) <= size);
+       mono_arch_flush_icache (start, code - start);
+       return start;
+}
+
+gpointer
+mono_arch_get_static_rgctx_trampoline (MonoMethod *m, MonoMethodRuntimeGenericContext *mrgctx, gpointer addr)
+{
+       guint8 *code, *start;
+       guint32 buf_len = 32;
+       MonoDomain *domain = mono_domain_get ();
+
+       start = code = mono_domain_code_reserve (domain, buf_len);
+       code = mono_arm_emit_imm64 (code, MONO_ARCH_RGCTX_REG, (guint64)mrgctx);
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)addr);
+       arm_brx (code, ARMREG_IP0);
+
+       g_assert ((code - start) <= buf_len);
+
+       mono_arch_flush_icache (start, code - start);
+
+       return start;
+}
+
+gpointer
+mono_arch_create_rgctx_lazy_fetch_trampoline (guint32 slot, MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int buf_size;
+       int i, depth, index, njumps;
+       gboolean is_mrgctx;
+       guint8 **rgctx_null_jumps;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+       guint8 *tramp;
+       guint32 code_len;
+
+       is_mrgctx = MONO_RGCTX_SLOT_IS_MRGCTX (slot);
+       index = MONO_RGCTX_SLOT_INDEX (slot);
+       if (is_mrgctx)
+               index += MONO_SIZEOF_METHOD_RUNTIME_GENERIC_CONTEXT / sizeof (gpointer);
+       for (depth = 0; ; ++depth) {
+               int size = mono_class_rgctx_get_array_size (depth, is_mrgctx);
+
+               if (index < size - 1)
+                       break;
+               index -= size - 1;
+       }
+
+       buf_size = 64 + 16 * depth;
+       code = buf = mono_global_codeman_reserve (buf_size);
+
+       rgctx_null_jumps = g_malloc0 (sizeof (guint8*) * (depth + 2));
+       njumps = 0;
+
+       /* The vtable/mrgtx is in R0 */
+       g_assert (MONO_ARCH_VTABLE_REG == ARMREG_R0);
+
+       if (is_mrgctx) {
+               /* get mrgctx ptr */
+               arm_movx (code, ARMREG_IP1, ARMREG_R0);
+       } else {
+               /* load rgctx ptr from vtable */
+               code = mono_arm_emit_ldrx (code, ARMREG_IP1, ARMREG_R0, MONO_STRUCT_OFFSET (MonoVTable, runtime_generic_context));
+               /* is the rgctx ptr null? */
+               /* if yes, jump to actual trampoline */
+               rgctx_null_jumps [njumps ++] = code;
+               arm_cbzx (code, ARMREG_IP1, 0);
+       }
+
+       for (i = 0; i < depth; ++i) {
+               /* load ptr to next array */
+               if (is_mrgctx && i == 0) {
+                       code = mono_arm_emit_ldrx (code, ARMREG_IP1, ARMREG_IP1, MONO_SIZEOF_METHOD_RUNTIME_GENERIC_CONTEXT);
+               } else {
+                       code = mono_arm_emit_ldrx (code, ARMREG_IP1, ARMREG_IP1, 0);
+               }
+               /* is the ptr null? */
+               /* if yes, jump to actual trampoline */
+               rgctx_null_jumps [njumps ++] = code;
+               arm_cbzx (code, ARMREG_IP1, 0);
+       }
+
+       /* fetch slot */
+       code = mono_arm_emit_ldrx (code, ARMREG_IP1, ARMREG_IP1, sizeof (gpointer) * (index + 1));
+       /* is the slot null? */
+       /* if yes, jump to actual trampoline */
+       rgctx_null_jumps [njumps ++] = code;
+       arm_cbzx (code, ARMREG_IP1, 0);
+       /* otherwise return, result is in IP1 */
+       arm_movx (code, ARMREG_R0, ARMREG_IP1);
+       arm_brx (code, ARMREG_LR);
+
+       g_assert (njumps <= depth + 2);
+       for (i = 0; i < njumps; ++i)
+               mono_arm_patch (rgctx_null_jumps [i], code, MONO_R_ARM64_CBZ);
+
+       g_free (rgctx_null_jumps);
+
+       /* Slowpath */
+
+       /* Call mono_rgctx_lazy_fetch_trampoline (), passing in the slot as argument */
+       /* The vtable/mrgctx is still in R0 */
+       if (aot) {
+               code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, g_strdup_printf ("specific_trampoline_lazy_fetch_%u", slot));
+       } else {
+               tramp = mono_arch_create_specific_trampoline (GUINT_TO_POINTER (slot), MONO_TRAMPOLINE_RGCTX_LAZY_FETCH, mono_get_root_domain (), &code_len);
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)tramp);
+       }
+       arm_brx (code, ARMREG_IP0);
+
+       mono_arch_flush_icache (buf, code - buf);
+
+       g_assert (code - buf <= buf_size);
+
+       if (info) {
+               char *name = mono_get_rgctx_fetch_trampoline_name (slot);
+               *info = mono_tramp_info_create (name, buf, code - buf, ji, unwind_ops);
+               g_free (name);
+       }
+
+       return buf;
+}
+
+gpointer
+mono_arch_create_general_rgctx_lazy_fetch_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int tramp_size;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+
+       g_assert (aot);
+
+       tramp_size = 32;
+
+       code = buf = mono_global_codeman_reserve (tramp_size);
+
+       mono_add_unwind_op_def_cfa (unwind_ops, code, buf, ARMREG_SP, 0);
+
+       // FIXME: Currently, we always go to the slow path.
+       /* Load trampoline addr */
+       arm_ldrx (code, ARMREG_IP0, MONO_ARCH_RGCTX_REG, 8);
+       /* The vtable/mrgctx is in R0 */
+       g_assert (MONO_ARCH_VTABLE_REG == ARMREG_R0);
+       arm_brx (code, ARMREG_IP0);
+
+       mono_arch_flush_icache (buf, code - buf);
+
+       g_assert (code - buf <= tramp_size);
+
+       if (info)
+               *info = mono_tramp_info_create ("rgctx_fetch_trampoline_general", buf, code - buf, ji, unwind_ops);
+
+       return buf;
+}
+
+static gpointer
+handler_block_trampoline_helper (gpointer *ptr)
+{
+       MonoJitTlsData *jit_tls = mono_native_tls_get_value (mono_jit_tls_id);
+       return jit_tls->handler_block_return_address;
+}
+
+gpointer
+mono_arch_create_handler_block_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *tramp;
+       guint8 *code, *buf;
+       int tramp_size = 64;
+       MonoJumpInfo *ji = NULL;
+       GSList *unwind_ops = NULL;
+
+       g_assert (!aot);
+
+       code = buf = mono_global_codeman_reserve (tramp_size);
+
+       unwind_ops = NULL;
+
+       tramp = mono_arch_create_specific_trampoline (NULL, MONO_TRAMPOLINE_HANDLER_BLOCK_GUARD, NULL, NULL);
+
+       /*
+       This trampoline restore the call chain of the handler block then jumps into the code that deals with it.
+       */
+
+       /*
+        * We are in a method frame after the call emitted by OP_CALL_HANDLER.
+        */
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)handler_block_trampoline_helper);
+       /* Set it as the return address so the trampoline will return to it */
+       arm_movx (code, ARMREG_LR, ARMREG_IP0);
+
+       /* Call the trampoline */
+       code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)tramp);
+       arm_brx (code, ARMREG_IP0);
+
+       mono_arch_flush_icache (buf, code - buf);
+       mono_profiler_code_buffer_new (buf, code - buf, MONO_PROFILER_CODE_BUFFER_HELPER, NULL);
+       g_assert (code - buf <= tramp_size);
+
+       *info = mono_tramp_info_create ("handler_block_trampoline", buf, code - buf, ji, unwind_ops);
+
+       return buf;
+}
+
+/*
+ * mono_arch_create_sdb_trampoline:
+ *
+ *   Return a trampoline which captures the current context, passes it to
+ * debugger_agent_single_step_from_context ()/debugger_agent_breakpoint_from_context (),
+ * then restores the (potentially changed) context.
+ */
+guint8*
+mono_arch_create_sdb_trampoline (gboolean single_step, MonoTrampInfo **info, gboolean aot)
+{
+       int tramp_size = 512;
+       int offset, imm, frame_size, ctx_offset;
+       guint64 gregs_regset;
+       guint8 *code, *buf;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+
+       code = buf = mono_global_codeman_reserve (tramp_size);
+
+       /* Compute stack frame size and offsets */
+       offset = 0;
+       /* frame block */
+       offset += 2 * 8;
+       /* MonoContext */
+       ctx_offset = offset;
+       offset += sizeof (MonoContext);
+       offset = ALIGN_TO (offset, MONO_ARCH_FRAME_ALIGNMENT);
+       frame_size = offset;
+
+       // FIXME: Unwind info
+
+       /* Setup stack frame */
+       imm = frame_size;
+       while (imm > 256) {
+               arm_subx_imm (code, ARMREG_SP, ARMREG_SP, 256);
+               imm -= 256;
+       }
+       arm_subx_imm (code, ARMREG_SP, ARMREG_SP, imm);
+       arm_stpx (code, ARMREG_FP, ARMREG_LR, ARMREG_SP, 0);
+       arm_movspx (code, ARMREG_FP, ARMREG_SP);
+
+       /* Initialize a MonoContext structure on the stack */
+       /* No need to save fregs */
+       gregs_regset = ~((1 << ARMREG_FP) | (1 << ARMREG_SP));
+       code = mono_arm_emit_store_regarray (code, gregs_regset, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, regs));
+       /* Save caller fp */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, 0);
+       arm_strx (code, ARMREG_IP1, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_FP * 8));
+       /* Save caller sp */
+       arm_movx (code, ARMREG_IP1, ARMREG_FP);
+       imm = frame_size;
+       while (imm > 256) {
+               arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, 256);
+               imm -= 256;
+       }
+       arm_addx_imm (code, ARMREG_IP1, ARMREG_IP1, imm);
+       arm_strx (code, ARMREG_IP1, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_SP * 8));
+       /* Save caller ip */
+       arm_ldrx (code, ARMREG_IP1, ARMREG_FP, 8);
+       arm_strx (code, ARMREG_IP1, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, pc));
+
+       /* Call the single step/breakpoint function in sdb */
+       /* Arg1 = ctx */
+       arm_addx_imm (code, ARMREG_R0, ARMREG_FP, ctx_offset);
+       if (aot) {
+               if (single_step)
+                       code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "debugger_agent_single_step_from_context");
+               else
+                       code = mono_arm_emit_aotconst (&ji, code, buf, ARMREG_IP0, MONO_PATCH_INFO_JIT_ICALL_ADDR, "debugger_agent_breakpoint_from_context");
+       } else {
+               gpointer addr = single_step ? debugger_agent_single_step_from_context : debugger_agent_breakpoint_from_context;
+
+               code = mono_arm_emit_imm64 (code, ARMREG_IP0, (guint64)addr);
+       }
+       arm_blrx (code, ARMREG_IP0);
+
+       /* Restore ctx */
+       /* Save fp/pc into the frame block */
+       arm_ldrx (code, ARMREG_IP0, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, regs) + (ARMREG_FP * 8));
+       arm_strx (code, ARMREG_IP0, ARMREG_FP, 0);
+       arm_ldrx (code, ARMREG_IP0, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, pc));
+       arm_strx (code, ARMREG_IP0, ARMREG_FP, 8);
+       gregs_regset = ~((1 << ARMREG_FP) | (1 << ARMREG_SP));
+       code = mono_arm_emit_load_regarray (code, gregs_regset, ARMREG_FP, ctx_offset + G_STRUCT_OFFSET (MonoContext, regs));
+
+       code = mono_arm_emit_destroy_frame (code, frame_size, ((1 << ARMREG_IP0) | (1 << ARMREG_IP1)));
+
+       arm_retx (code, ARMREG_LR);
+
+       mono_arch_flush_icache (code, code - buf);
+       g_assert (code - buf <= tramp_size);
+
+       const char *tramp_name = single_step ? "sdb_single_step_trampoline" : "sdb_breakpoint_trampoline";
+       *info = mono_tramp_info_create (tramp_name, buf, code - buf, ji, unwind_ops);
+
+       return buf;
+}
+
+#else /* DISABLE_JIT */
+
+guchar*
+mono_arch_create_generic_trampoline (MonoTrampolineType tramp_type, MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_create_specific_trampoline (gpointer arg1, MonoTrampolineType tramp_type, MonoDomain *domain, guint32 *code_len)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_create_handler_block_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+        g_assert_not_reached ();
+        return NULL;
+}
+
+gpointer
+mono_arch_get_unbox_trampoline (MonoMethod *m, gpointer addr)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_static_rgctx_trampoline (MonoMethod *m, MonoMethodRuntimeGenericContext *mrgctx, gpointer addr)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_create_rgctx_lazy_fetch_trampoline (guint32 slot, MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+gpointer
+mono_arch_get_nullified_class_init_trampoline (MonoTrampInfo **info)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+guint8*
+mono_arch_create_sdb_trampoline (gboolean single_step, MonoTrampInfo **info, gboolean aot)
+{
+       g_assert_not_reached ();
+       return NULL;
+}
+
+#endif /* !DISABLE_JIT */
index eb61dc05cd4771475e8771c1572ac1ff4218fc22..408997daace8d426c6ba6ffaf4a81c9b8eea032c 100644 (file)
@@ -13,7 +13,7 @@
 /*              Dietmar Maurer (dietmar@ximian.com)                */
 /*                                                                 */
 /* Copyright   - 2001 Ximian, Inc.                                 */
-/*                                                                 */
+/* Licensed under the MIT license. See LICENSE file in the project root for full license information.*/
 /*------------------------------------------------------------------*/
 
 /*------------------------------------------------------------------*/
diff --git a/mono/mini/tramp-x86-gsharedvt.c b/mono/mini/tramp-x86-gsharedvt.c
new file mode 100644 (file)
index 0000000..5482504
--- /dev/null
@@ -0,0 +1,360 @@
+/*
+ * tramp-x86-gsharedvt.c: gsharedvt support code for x86
+ *
+ * Authors:
+ *   Zoltan Varga <vargaz@gmail.com>
+ *
+ * Copyright 2013 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ */
+#include "mini.h"
+#include <mono/metadata/abi-details.h>
+
+#ifdef MONO_ARCH_GSHAREDVT_SUPPORTED
+
+gpointer
+mono_x86_start_gsharedvt_call (GSharedVtCallInfo *info, gpointer *caller, gpointer *callee, gpointer mrgctx_reg)
+{
+       int i;
+       int *map = info->map;
+
+       /* Set vtype ret arg */
+       if (info->vret_arg_slot != -1) {
+               callee [info->vret_arg_slot] = &callee [info->vret_slot];
+       }
+       /* Copy data from the caller argument area to the callee */
+       for (i = 0; i < info->map_count; ++i) {
+               int src = map [i * 2];
+               int dst = map [i * 2 + 1];
+
+               switch ((src >> 16) & 0x3) {
+               case 0:
+                       callee [dst] = caller [src];
+                       break;
+               case 1: {
+                       int j, nslots;
+                       gpointer *arg;
+
+                       /* gsharedvt->normal */
+                       nslots = src >> 18;
+                       arg = (gpointer*)caller [src & 0xffff];
+                       for (j = 0; j < nslots; ++j)
+                               callee [dst + j] = arg [j];
+                       break;
+               }
+               case 2:
+                       /* gsharedvt arg, have to take its address */
+                       callee [dst] = caller + (src & 0xffff);
+                       break;
+#if 0
+               int dst = map [i * 2 + 1];
+               if (dst >= 0xffff) {
+                       /* gsharedvt arg, have to take its address */
+                       callee [dst - 0xffff] = caller + map [i * 2];
+               } else {
+                       callee [dst] = caller [map [i * 2]];
+               }
+#endif
+               }
+       }
+
+       if (info->vcall_offset != -1) {
+               MonoObject *this_obj = caller [0];
+
+               if (G_UNLIKELY (!this_obj))
+                       return NULL;
+               if (info->vcall_offset == MONO_GSHAREDVT_DEL_INVOKE_VT_OFFSET)
+                       /* delegate invoke */
+                       return ((MonoDelegate*)this_obj)->invoke_impl;
+               else
+                       return *(gpointer*)((char*)this_obj->vtable + info->vcall_offset);
+       } else if (info->calli) {
+               /* The address to call is passed in the mrgctx reg */
+               return mrgctx_reg;
+       } else {
+               return info->addr;
+       }
+
+}
+
+gpointer
+mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
+{
+       guint8 *code, *buf;
+       int buf_len, cfa_offset;
+       GSList *unwind_ops = NULL;
+       MonoJumpInfo *ji = NULL;
+       guint8 *br_out, *br [16];
+       int info_offset, mrgctx_offset;
+
+       buf_len = 320;
+       buf = code = mono_global_codeman_reserve (buf_len);
+
+       /*
+        * This trampoline is responsible for marshalling calls between normal code and gsharedvt code. The
+        * caller is a normal or gshared method which uses the signature of the inflated method to make the call, while
+        * the callee is a gsharedvt method which has a signature which uses valuetypes in place of type parameters, i.e.
+        * caller:
+        * foo<bool> (bool b)
+        * callee:
+        * T=<type used to represent vtype type arguments, currently TypedByRef>
+        * foo<T> (T b)
+        * The trampoline is responsible for marshalling the arguments and marshalling the result back. To simplify
+        * things, we create our own stack frame, and do most of the work in a C function, which receives a
+        * GSharedVtCallInfo structure as an argument. The structure should contain information to execute the C function to
+        * be as fast as possible. The argument is received in EAX from a gsharedvt trampoline. So the real
+        * call sequence looks like this:
+        * caller -> gsharedvt trampoline -> gsharevt in trampoline -> start_gsharedvt_call
+        * FIXME: Optimize this.
+        */
+
+       cfa_offset = sizeof (gpointer);
+       mono_add_unwind_op_def_cfa (unwind_ops, code, buf, X86_ESP, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, X86_NREG, -cfa_offset);
+       x86_push_reg (code, X86_EBP);
+       cfa_offset += sizeof (gpointer);
+       mono_add_unwind_op_def_cfa_offset (unwind_ops, code, buf, cfa_offset);
+       mono_add_unwind_op_offset (unwind_ops, code, buf, X86_EBP, - cfa_offset);
+       x86_mov_reg_reg (code, X86_EBP, X86_ESP, sizeof (gpointer));
+       mono_add_unwind_op_def_cfa_reg (unwind_ops, code, buf, X86_EBP);
+       /* Alloc stack frame/align stack */
+       x86_alu_reg_imm (code, X86_SUB, X86_ESP, 8);
+       info_offset = -4;
+       mrgctx_offset = - 8;
+       /* The info struct is put into EAX by the gsharedvt trampoline */
+       /* Save info struct addr */
+       x86_mov_membase_reg (code, X86_EBP, info_offset, X86_EAX, 4);
+       /* Save rgctx */
+       x86_mov_membase_reg (code, X86_EBP, mrgctx_offset, MONO_ARCH_RGCTX_REG, 4);
+
+       /* Allocate stack area used to pass arguments to the method */
+       x86_mov_reg_membase (code, X86_EAX, X86_EAX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, stack_usage), sizeof (gpointer));
+       x86_alu_reg_reg (code, X86_SUB, X86_ESP, X86_EAX);
+
+#if 0
+       /* Stack alignment check */
+       x86_mov_reg_reg (code, X86_ECX, X86_ESP, 4);
+       x86_alu_reg_imm (code, X86_AND, X86_ECX, MONO_ARCH_FRAME_ALIGNMENT - 1);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, 0);
+       x86_branch_disp (code, X86_CC_EQ, 3, FALSE);
+       x86_breakpoint (code);
+#endif
+
+       /* ecx = caller argument area */
+       x86_mov_reg_reg (code, X86_ECX, X86_EBP, 4);
+       x86_alu_reg_imm (code, X86_ADD, X86_ECX, 8);
+       /* eax = callee argument area */
+       x86_mov_reg_reg (code, X86_EAX, X86_ESP, 4);
+
+       /* Call start_gsharedvt_call */
+       /* Arg 4 */
+       x86_push_membase (code, X86_EBP, mrgctx_offset);
+       /* Arg3 */
+       x86_push_reg (code, X86_EAX);
+       /* Arg2 */
+       x86_push_reg (code, X86_ECX);
+       /* Arg1 */
+       x86_push_membase (code, X86_EBP, info_offset);
+       if (aot) {
+               code = mono_arch_emit_load_aotconst (buf, code, &ji, MONO_PATCH_INFO_JIT_ICALL_ADDR, "mono_x86_start_gsharedvt_call");
+               x86_call_reg (code, X86_EAX);
+       } else {
+               x86_call_code (code, mono_x86_start_gsharedvt_call);
+       }
+       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 4 * 4);
+       /* The address to call is in eax */
+       /* The stack is now setup for the real call */
+       /* Load info struct */
+       x86_mov_reg_membase (code, X86_ECX, X86_EBP, info_offset, 4);
+       /* Load rgctx */
+       x86_mov_reg_membase (code, MONO_ARCH_RGCTX_REG, X86_EBP, mrgctx_offset, sizeof (gpointer));
+       /* Make the call */
+       x86_call_reg (code, X86_EAX);
+       /* The return value is either in registers, or stored to an area beginning at sp [info->vret_slot] */
+       /* EAX/EDX might contain the return value, only ECX is free */
+       /* Load info struct */
+       x86_mov_reg_membase (code, X86_ECX, X86_EBP, info_offset, 4);
+
+       /* Branch to the in/out handling code */
+       x86_alu_membase_imm (code, X86_CMP, X86_ECX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, gsharedvt_in), 1);  
+       br_out = code;
+       x86_branch32 (code, X86_CC_NE, 0, TRUE);
+
+       /*
+        * IN CASE
+        */
+
+       /* Load ret marshal type */
+       x86_mov_reg_membase (code, X86_ECX, X86_ECX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal), 4);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_NONE);
+       br [0] = code;
+       x86_branch8 (code, X86_CC_NE, 0, TRUE);
+
+       /* Normal return, no marshalling required */
+       x86_leave (code);
+       x86_ret (code);
+
+       /* Return value marshalling */
+       x86_patch (br [0], code);
+       /* Load info struct */
+       x86_mov_reg_membase (code, X86_EAX, X86_EBP, info_offset, 4);
+       /* Load 'vret_slot' */
+       x86_mov_reg_membase (code, X86_EAX, X86_EAX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_slot), 4);
+       /* Compute ret area address */
+       x86_shift_reg_imm (code, X86_SHL, X86_EAX, 2);
+       x86_alu_reg_reg (code, X86_ADD, X86_EAX, X86_ESP);
+       /* The callee does a ret $4, so sp is off by 4 */
+       x86_alu_reg_imm (code, X86_SUB, X86_EAX, sizeof (gpointer));
+
+       /* Branch to specific marshalling code */
+       // FIXME: Move the I4 case to the top */
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_DOUBLE_FPSTACK);
+       br [1] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_FLOAT_FPSTACK);
+       br [2] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_STACK_POP);
+       br [3] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_I1);
+       br [4] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_U1);
+       br [5] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_I2);
+       br [6] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_U2);
+       br [7] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       /* IREGS case */
+       /* Load both eax and edx for simplicity */
+       x86_mov_reg_membase (code, X86_EDX, X86_EAX, sizeof (gpointer), sizeof (gpointer));
+       x86_mov_reg_membase (code, X86_EAX, X86_EAX, 0, sizeof (gpointer));
+       x86_leave (code);
+       x86_ret (code);
+       /* DOUBLE_FPSTACK case */
+       x86_patch (br [1], code);
+       x86_fld_membase (code, X86_EAX, 0, TRUE);
+       x86_jump8 (code, 0);
+       x86_leave (code);
+       x86_ret (code);
+       /* FLOAT_FPSTACK case */
+       x86_patch (br [2], code);
+       x86_fld_membase (code, X86_EAX, 0, FALSE);
+       x86_leave (code);
+       x86_ret (code);
+       /* STACK_POP case */
+       x86_patch (br [3], code);
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+       /* I1 case */
+       x86_patch (br [4], code);
+       x86_widen_membase (code, X86_EAX, X86_EAX, 0, TRUE, FALSE);
+       x86_leave (code);
+       x86_ret (code);
+       /* U1 case */
+       x86_patch (br [5], code);
+       x86_widen_membase (code, X86_EAX, X86_EAX, 0, FALSE, FALSE);
+       x86_leave (code);
+       x86_ret (code);
+       /* I2 case */
+       x86_patch (br [6], code);
+       x86_widen_membase (code, X86_EAX, X86_EAX, 0, TRUE, TRUE);
+       x86_leave (code);
+       x86_ret (code);
+       /* U2 case */
+       x86_patch (br [7], code);
+       x86_widen_membase (code, X86_EAX, X86_EAX, 0, FALSE, TRUE);
+       x86_leave (code);
+       x86_ret (code);
+
+       /*
+        * OUT CASE
+        */
+
+       x86_patch (br_out, code);
+       /* Load ret marshal type into ECX */
+       x86_mov_reg_membase (code, X86_ECX, X86_ECX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, ret_marshal), 4);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_NONE);
+       br [0] = code;
+       x86_branch8 (code, X86_CC_NE, 0, TRUE);
+
+       /* Normal return, no marshalling required */
+       x86_leave (code);
+       x86_ret (code);
+
+       /* Return value marshalling */
+       x86_patch (br [0], code);
+
+       /* EAX might contain the return value */
+       // FIXME: Use moves
+       x86_push_reg (code, X86_EAX);
+
+       /* Load info struct */
+       x86_mov_reg_membase (code, X86_EAX, X86_EBP, info_offset, 4);
+       /* Load 'vret_arg_slot' */
+       x86_mov_reg_membase (code, X86_EAX, X86_EAX, MONO_STRUCT_OFFSET (GSharedVtCallInfo, vret_arg_slot), 4);
+       /* Compute ret area address in the caller frame in EAX */
+       x86_shift_reg_imm (code, X86_SHL, X86_EAX, 2);
+       x86_alu_reg_reg (code, X86_ADD, X86_EAX, X86_EBP);
+       x86_alu_reg_imm (code, X86_ADD, X86_EAX, 8);
+       x86_mov_reg_membase (code, X86_EAX, X86_EAX, 0, sizeof (gpointer));
+
+       /* Branch to specific marshalling code */
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_DOUBLE_FPSTACK);
+       br [1] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_FLOAT_FPSTACK);
+       br [2] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_STACK_POP);
+       br [3] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       x86_alu_reg_imm (code, X86_CMP, X86_ECX, GSHAREDVT_RET_IREGS);
+       br [4] = code;
+       x86_branch8 (code, X86_CC_E, 0, TRUE);
+       /* IREG case */
+       x86_mov_reg_reg (code, X86_ECX, X86_EAX, sizeof (gpointer));
+       x86_pop_reg (code, X86_EAX);
+       x86_mov_membase_reg (code, X86_ECX, 0, X86_EAX, sizeof (gpointer));
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+       /* IREGS case */
+       x86_patch (br [4], code);
+       x86_mov_reg_reg (code, X86_ECX, X86_EAX, sizeof (gpointer));
+       x86_pop_reg (code, X86_EAX);
+       x86_mov_membase_reg (code, X86_ECX, sizeof (gpointer), X86_EDX, sizeof (gpointer));
+       x86_mov_membase_reg (code, X86_ECX, 0, X86_EAX, sizeof (gpointer));
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+       /* DOUBLE_FPSTACK case */
+       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 4);
+       x86_patch (br [1], code);
+       x86_fst_membase (code, X86_EAX, 0, TRUE, TRUE);
+       x86_jump8 (code, 0);
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+       /* FLOAT_FPSTACK case */
+       x86_alu_reg_imm (code, X86_ADD, X86_ESP, 4);
+       x86_patch (br [2], code);
+       x86_fst_membase (code, X86_EAX, 0, FALSE, TRUE);
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+       /* STACK_POP case */
+       x86_patch (br [3], code);
+       x86_leave (code);
+       x86_ret_imm (code, 4);
+
+       g_assert ((code - buf) < buf_len);
+
+       if (info)
+               *info = mono_tramp_info_create ("gsharedvt_trampoline", buf, code - buf, ji, unwind_ops);
+
+       mono_arch_flush_icache (buf, code - buf);
+       return buf;
+}
+
+#endif /* MONO_ARCH_GSHAREDVT_SUPPORTED */
index e416527c2b3ceb59d8979a129a84384581520cfe..dd560843018d8a2a3a59b8917eb25aada8874680 100644 (file)
@@ -878,17 +878,3 @@ mono_arch_create_sdb_trampoline (gboolean single_step, MonoTrampInfo **info, gbo
        return buf;
 }
 
-#if defined(ENABLE_GSHAREDVT)
-
-#include "../../../mono-extensions/mono/mini/tramp-x86-gsharedvt.c"
-
-#else
-
-gpointer
-mono_arch_get_gsharedvt_trampoline (MonoTrampInfo **info, gboolean aot)
-{
-       *info = NULL;
-       return NULL;
-}
-
-#endif /* !MONOTOUCH */
index 82f14d7882255940ad311339fbe8c50073075a1b..ef3c65a7f225790813dfa5ab71f9a5e11b8c8ed4 100644 (file)
@@ -652,8 +652,12 @@ mono_unwind_cleanup (void)
 
                g_free (cached);
        }
-
        g_free (cached_info);
+
+       for (GSList *cursor = cached_info_list; cursor != NULL; cursor = cursor->next)
+               g_free (cursor->data);
+
+       g_slist_free (cached_info_list);
 }
 
 /*
@@ -708,10 +712,10 @@ mono_cache_unwind_info (guint8 *unwind_info, guint32 unwind_info_len)
 
                mono_memory_barrier ();
 
-               cached_info = new_table;
-
                cached_info_list = g_slist_prepend (cached_info_list, cached_info);
 
+               cached_info = new_table;
+
                cached_info_size *= 2;
        }
 
index 0e051966e126822f7121977b87b7aed82b1a2005..bbf90a08b64aac4af029668e370ba1778036466c 100644 (file)
@@ -162,7 +162,7 @@ mono_xdebug_init (const char *options)
 
        mono_img_writer_emit_start (w);
 
-       xdebug_writer = mono_dwarf_writer_create (w, il_file, 0, TRUE, TRUE);
+       xdebug_writer = mono_dwarf_writer_create (w, il_file, 0, TRUE);
 
        /* Emit something so the file has a text segment */
        mono_img_writer_emit_section_change (w, ".text", 0);
@@ -185,7 +185,7 @@ xdebug_begin_emit (MonoImageWriter **out_w, MonoDwarfWriter **out_dw)
        if (!il_file)
                il_file = fopen ("xdb.il", "w");
 
-       dw = mono_dwarf_writer_create (w, il_file, il_file_line_index, FALSE, TRUE);
+       dw = mono_dwarf_writer_create (w, il_file, il_file_line_index, TRUE);
 
        mono_dwarf_writer_emit_base_info (dw, "JITted code", mono_unwind_get_cie_program ());
 
index 39cf237bf87a15ac51d69d4da8c1eee9f47cc52d..6ae3d2556e90c46cd2cba6631b4c60cb4814d5f1 100644 (file)
@@ -61,21 +61,21 @@ LIBMONO=$(top_builddir)/mono/mini/libmonosgen-$(API_VER).la
 endif
 
 libmono_profiler_aot_la_SOURCES = mono-profiler-aot.c
-libmono_profiler_aot_la_LIBADD = $(LIBMONO) $(GLIB_LIBS) $(LIBICONV)
+libmono_profiler_aot_la_LIBADD = $(GLIB_LIBS) $(LIBICONV)
 if BITCODE
 libmono_profiler_aot_la_LDFLAGS = -no-undefined
 endif
 libmono_profiler_iomap_la_SOURCES = mono-profiler-iomap.c
-libmono_profiler_iomap_la_LIBADD = $(LIBMONO) $(GLIB_LIBS) $(LIBICONV)
+libmono_profiler_iomap_la_LIBADD = $(GLIB_LIBS) $(LIBICONV)
 if BITCODE
 libmono_profiler_iomap_la_LDFLAGS = -no-undefined
 endif
 libmono_profiler_log_la_SOURCES = proflog.c
-libmono_profiler_log_la_LIBADD = $(LIBMONO) $(GLIB_LIBS) $(Z_LIBS)
+libmono_profiler_log_la_LIBADD = $(GLIB_LIBS) $(Z_LIBS)
 if HAVE_VTUNE
 libmono_profiler_vtune_la_SOURCES = mono-profiler-vtune.c
 libmono_profiler_vtune_la_CFLAGS = $(VTUNE_CFLAGS)
-libmono_profiler_vtune_la_LIBADD = $(VTUNE_LIBS) $(LIBMONO) $(GLIB_LIBS) $(LIBICONV)
+libmono_profiler_vtune_la_LIBADD = $(VTUNE_LIBS) $(GLIB_LIBS) $(LIBICONV)
 endif
 
 # The log profile uses eglib functions, so it needs to be linked against
index e57211635ee700b0ea1bea48015d8709333b89fd..e8d53afea686ed76588370c99fe74beac2c0718b 100644 (file)
@@ -6,6 +6,7 @@
  *   Alex Rønne Petersen (alexrp@xamarin.com)
  *
  * Copyright 2010 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
@@ -353,6 +354,7 @@ section_name (int section)
        case MONO_COUNTER_SECURITY: return "Mono Security";
        case MONO_COUNTER_RUNTIME: return "Mono Runtime";
        case MONO_COUNTER_SYSTEM: return "Mono System";
+       case MONO_COUNTER_PROFILER: return "Mono Profiler";
        default: return "<unknown>";
        }
 }
@@ -2255,8 +2257,6 @@ decode_buffer (ProfContext *ctx)
                        time_from += startup_time;
                        time_to += startup_time;
                }
-               if (!thread->name)
-                       thread->name = pstrdup ("Main");
        }
        for (i = 0; i < thread->stack_id; ++i)
                thread->stack [i]->recurse_count++;
@@ -3151,7 +3151,9 @@ dump_threads (ProfContext *ctx)
        ThreadContext *thread;
        fprintf (outfile, "\nThread summary\n");
        for (thread = ctx->threads; thread; thread = thread->next) {
-               fprintf (outfile, "\tThread: %p, name: \"%s\"\n", (void*)thread->thread_id, thread->name? thread->name: "");
+               if (thread->thread_id) {
+                       fprintf (outfile, "\tThread: %p, name: \"%s\"\n", (void*)thread->thread_id, thread->name? thread->name: "");
+               }
        }
 }
 
index 79d80717aaabb9fed6e46a05a8403e7a5f2cd43e..4cf48bbd1b2491a54e3155c2c793b1934d5bb441 100644 (file)
@@ -9,6 +9,7 @@
  * The AOT compiler can load these files during compilation.
  * Currently, only the order in which methods were compiled is saved, 
  * allowing more efficient function ordering in the AOT files.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 7030a4b3e5fa4149528fda724c8c49e8fd51a321..e658bf9777b6b78e81c6851a74b41a6fc44ec53a 100644 (file)
@@ -8,6 +8,7 @@
  *
  * Note: this profiler is completely unsafe wrt handling managed objects,
  * don't use and don't copy code from here.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 
@@ -17,6 +18,7 @@
 #include <mono/metadata/metadata-internals.h>
 #include <mono/metadata/class.h>
 #include <mono/metadata/class-internals.h>
+#include <mono/metadata/object-internals.h>
 #include <mono/metadata/image.h>
 #include <mono/metadata/mono-debug.h>
 #include <mono/metadata/debug-helpers.h>
@@ -184,6 +186,7 @@ static inline guint32 calc_strings_hash (const gchar *str1, const gchar *str2, g
 
 static inline void print_report (const gchar *format, ...)
 {
+       MonoError error;
        MonoClass *klass;
        MonoProperty *prop;
        MonoString *str;
@@ -198,7 +201,8 @@ static inline void print_report (const gchar *format, ...)
        klass = mono_class_load_from_name (mono_get_corlib (), "System", "Environment");
        mono_class_init (klass);
        prop = mono_class_get_property_from_name (klass, "StackTrace");
-       str = (MonoString*)mono_property_get_value (prop, NULL, NULL, NULL);
+       str = (MonoString*)mono_property_get_value_checked (prop, NULL, NULL, &error);
+       mono_error_assert_ok (&error);
        stack_trace = mono_string_to_utf8 (str);
 
        fprintf (stdout, "-= Stack Trace =-\n%s\n\n", stack_trace);
index cb2ea092fb3cdd739df3308daa6002b7cdc87258..23605903f4350f01b1a6c982b077a56648aae204 100644 (file)
@@ -7,10 +7,12 @@
  *
  * Copyright 2010 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
 #include "../mini/jit.h"
+#include "../metadata/metadata-internals.h"
 #include <mono/metadata/profiler.h>
 #include <mono/metadata/threads.h>
 #include <mono/metadata/mono-gc.h>
 #include <mono/metadata/tabledefs.h>
 #include <mono/utils/atomic.h>
 #include <mono/utils/mono-membar.h>
+#include <mono/utils/mono-mmap.h>
 #include <mono/utils/mono-counters.h>
 #include <mono/utils/mono-os-mutex.h>
 #include <mono/utils/mono-conc-hashtable.h>
+#include <mono/utils/lock-free-alloc.h>
 #include <mono/utils/lock-free-queue.h>
 #include <stdlib.h>
 #include <string.h>
@@ -120,6 +124,24 @@ static int do_counters = 0;
 static int do_coverage = 0;
 static gboolean debug_coverage = FALSE;
 static MonoProfileSamplingMode sampling_mode = MONO_PROFILER_STAT_MODE_PROCESS;
+static int max_allocated_sample_hits;
+
+static gint32 sample_hits;
+static gint32 sample_flushes;
+static gint32 sample_allocations;
+static gint32 buffer_allocations;
+static gint32 thread_starts;
+static gint32 thread_ends;
+static gint32 domain_loads;
+static gint32 domain_unloads;
+static gint32 context_loads;
+static gint32 context_unloads;
+static gint32 assembly_loads;
+static gint32 assembly_unloads;
+static gint32 image_loads;
+static gint32 image_unloads;
+static gint32 class_loads;
+static gint32 class_unloads;
 
 typedef struct _LogBuffer LogBuffer;
 
@@ -415,8 +437,12 @@ typedef struct _LogBuffer LogBuffer;
  * be done to the format.
  */
 
+// Pending data to be written to the log, for a single thread.
+// Threads periodically flush their own LogBuffers by calling safe_send
 struct _LogBuffer {
+       // Next (older) LogBuffer in processing queue
        LogBuffer *next;
+
        uint64_t time_base;
        uint64_t last_time;
        uintptr_t ptr_base;
@@ -424,11 +450,19 @@ struct _LogBuffer {
        uintptr_t last_method;
        uintptr_t obj_base;
        uintptr_t thread_id;
-       unsigned char* data_end;
-       unsigned char* data;
        int locked;
-       int size;
        int call_depth;
+
+       // Bytes allocated for this LogBuffer
+       int size;
+
+       // Start of currently unused space in buffer
+       unsigned char* cursor;
+
+       // Pointer to start-of-structure-plus-size (for convenience)
+       unsigned char* buf_end;
+
+       // Start of data in buffer. Contents follow "buffer format" described above.
        unsigned char buf [1];
 };
 
@@ -440,15 +474,6 @@ ign_res (int G_GNUC_UNUSED unused, ...)
 #define ENTER_LOG(lb,str) if ((lb)->locked) {ign_res (write(2, str, strlen(str))); ign_res (write(2, "\n", 1));return;} else {(lb)->locked++;}
 #define EXIT_LOG(lb) (lb)->locked--;
 
-typedef struct _StatBuffer StatBuffer;
-struct _StatBuffer {
-       StatBuffer *next;
-       uintptr_t size;
-       uintptr_t *data_end;
-       uintptr_t *data;
-       uintptr_t buf [1];
-};
-
 typedef struct _BinaryObject BinaryObject;
 
 struct _BinaryObject {
@@ -458,7 +483,6 @@ struct _BinaryObject {
 };
 
 struct _MonoProfiler {
-       StatBuffer *stat_buffers;
        FILE* file;
 #if defined (HAVE_SYS_ZLIB)
        gzFile gzfile;
@@ -472,14 +496,21 @@ struct _MonoProfiler {
 #ifndef HOST_WIN32
        pthread_t helper_thread;
        pthread_t writer_thread;
+       pthread_t dumper_thread;
 #endif
        volatile gint32 run_writer_thread;
        MonoLockFreeQueue writer_queue;
+       MonoSemType writer_queue_sem;
        MonoConcurrentHashTable *method_table;
        mono_mutex_t method_table_mutex;
+       volatile gint32 run_dumper_thread;
+       MonoLockFreeQueue dumper_queue;
+       MonoSemType dumper_queue_sem;
+       MonoLockFreeAllocSizeClass sample_size_class;
+       MonoLockFreeAllocator sample_allocator;
+       MonoLockFreeQueue sample_reuse_queue;
        BinaryObject *binary_objects;
        GPtrArray *coverage_filters;
-       GPtrArray *sorted_sample_events;
 };
 
 typedef struct _WriterQueueEntry WriterQueueEntry;
@@ -531,25 +562,18 @@ pstrdup (const char *s)
        return p;
 }
 
-static StatBuffer*
-create_stat_buffer (void)
-{
-       StatBuffer* buf = (StatBuffer *)alloc_buffer (BUFFER_SIZE);
-       buf->size = BUFFER_SIZE;
-       buf->data_end = (uintptr_t*)((unsigned char*)buf + buf->size);
-       buf->data = buf->buf;
-       return buf;
-}
-
 static LogBuffer*
 create_buffer (void)
 {
        LogBuffer* buf = (LogBuffer *)alloc_buffer (BUFFER_SIZE);
+
+       InterlockedIncrement (&buffer_allocations);
+
        buf->size = BUFFER_SIZE;
        buf->time_base = current_time ();
        buf->last_time = buf->time_base;
-       buf->data_end = (unsigned char*)buf + buf->size;
-       buf->data = buf->buf;
+       buf->buf_end = (unsigned char*)buf + buf->size;
+       buf->cursor = buf->buf;
        return buf;
 }
 
@@ -572,7 +596,7 @@ init_thread (void)
 static LogBuffer *
 ensure_logbuf_inner (LogBuffer *old, int bytes)
 {
-       if (old && old->data + bytes + 100 < old->data_end)
+       if (old && old->cursor + bytes + 100 < old->buf_end)
                return old;
 
        LogBuffer *new_ = (LogBuffer *)create_buffer ();
@@ -603,16 +627,16 @@ ensure_logbuf (int bytes)
 static void
 emit_byte (LogBuffer *logbuffer, int value)
 {
-       logbuffer->data [0] = value;
-       logbuffer->data++;
-       assert (logbuffer->data <= logbuffer->data_end);
+       logbuffer->cursor [0] = value;
+       logbuffer->cursor++;
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
 emit_value (LogBuffer *logbuffer, int value)
 {
-       encode_uleb128 (value, logbuffer->data, &logbuffer->data);
-       assert (logbuffer->data <= logbuffer->data_end);
+       encode_uleb128 (value, logbuffer->cursor, &logbuffer->cursor);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
@@ -623,25 +647,25 @@ emit_time (LogBuffer *logbuffer, uint64_t value)
        //      printf ("time went backwards\n");
        //if (tdiff > 1000000)
        //      printf ("large time offset: %llu\n", tdiff);
-       encode_uleb128 (tdiff, logbuffer->data, &logbuffer->data);
+       encode_uleb128 (tdiff, logbuffer->cursor, &logbuffer->cursor);
        /*if (tdiff != decode_uleb128 (p, &p))
                printf ("incorrect encoding: %llu\n", tdiff);*/
        logbuffer->last_time = value;
-       assert (logbuffer->data <= logbuffer->data_end);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
 emit_svalue (LogBuffer *logbuffer, int64_t value)
 {
-       encode_sleb128 (value, logbuffer->data, &logbuffer->data);
-       assert (logbuffer->data <= logbuffer->data_end);
+       encode_sleb128 (value, logbuffer->cursor, &logbuffer->cursor);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
 emit_uvalue (LogBuffer *logbuffer, uint64_t value)
 {
-       encode_uleb128 (value, logbuffer->data, &logbuffer->data);
-       assert (logbuffer->data <= logbuffer->data_end);
+       encode_uleb128 (value, logbuffer->cursor, &logbuffer->cursor);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
@@ -650,7 +674,7 @@ emit_ptr (LogBuffer *logbuffer, void *ptr)
        if (!logbuffer->ptr_base)
                logbuffer->ptr_base = (uintptr_t)ptr;
        emit_svalue (logbuffer, (intptr_t)ptr - logbuffer->ptr_base);
-       assert (logbuffer->data <= logbuffer->data_end);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
@@ -660,9 +684,9 @@ emit_method_inner (LogBuffer *logbuffer, void *method)
                logbuffer->method_base = (intptr_t)method;
                logbuffer->last_method = (intptr_t)method;
        }
-       encode_sleb128 ((intptr_t)((char*)method - (char*)logbuffer->last_method), logbuffer->data, &logbuffer->data);
+       encode_sleb128 ((intptr_t)((char*)method - (char*)logbuffer->last_method), logbuffer->cursor, &logbuffer->cursor);
        logbuffer->last_method = (intptr_t)method;
-       assert (logbuffer->data <= logbuffer->data_end);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 /*
@@ -754,7 +778,7 @@ emit_obj (LogBuffer *logbuffer, void *ptr)
        if (!logbuffer->obj_base)
                logbuffer->obj_base = (uintptr_t)ptr >> 3;
        emit_svalue (logbuffer, ((uintptr_t)ptr >> 3) - logbuffer->obj_base);
-       assert (logbuffer->data <= logbuffer->data_end);
+       assert (logbuffer->cursor <= logbuffer->buf_end);
 }
 
 static void
@@ -854,6 +878,7 @@ send_buffer (MonoProfiler *prof, GPtrArray *methods, LogBuffer *buffer)
        entry->methods = methods;
        entry->buffer = buffer;
        mono_lock_free_queue_enqueue (&prof->writer_queue, &entry->node);
+       mono_os_sem_post (&prof->writer_queue_sem);
 }
 
 static void
@@ -864,7 +889,7 @@ dump_buffer (MonoProfiler *profiler, LogBuffer *buf)
        if (buf->next)
                dump_buffer (profiler, buf->next);
        p = write_int32 (p, BUF_ID);
-       p = write_int32 (p, buf->data - buf->buf);
+       p = write_int32 (p, buf->cursor - buf->buf);
        p = write_int64 (p, buf->time_base);
        p = write_int64 (p, buf->ptr_base);
        p = write_int64 (p, buf->obj_base);
@@ -873,11 +898,11 @@ dump_buffer (MonoProfiler *profiler, LogBuffer *buf)
 #if defined (HAVE_SYS_ZLIB)
        if (profiler->gzfile) {
                gzwrite (profiler->gzfile, hbuf, p - hbuf);
-               gzwrite (profiler->gzfile, buf->buf, buf->data - buf->buf);
+               gzwrite (profiler->gzfile, buf->buf, buf->cursor - buf->buf);
        } else {
 #endif
                fwrite (hbuf, p - hbuf, 1, profiler->file);
-               fwrite (buf->buf, buf->data - buf->buf, 1, profiler->file);
+               fwrite (buf->buf, buf->cursor - buf->buf, 1, profiler->file);
                fflush (profiler->file);
 #if defined (HAVE_SYS_ZLIB)
        }
@@ -893,7 +918,7 @@ process_requests (MonoProfiler *profiler)
 }
 
 static void counters_init (MonoProfiler *profiler);
-static void counters_sample (MonoProfiler *profiler, uint64_t timestamp);
+static void counters_sample (MonoProfiler *profiler, uint64_t timestamp, gboolean threadless);
 
 /*
  * Can be called only at safe callback locations.
@@ -923,6 +948,15 @@ safe_send (MonoProfiler *profiler, LogBuffer *logbuffer)
        TLS_GET (LogBuffer, tlsbuffer)->call_depth = cd;
 }
 
+static void
+safe_send_threadless (MonoProfiler *prof, LogBuffer *buf)
+{
+       for (LogBuffer *iter = buf; iter; iter = iter->next)
+               iter->thread_id = 0;
+
+       safe_send (prof, buf);
+}
+
 static int
 gc_reference (MonoObject *obj, MonoClass *klass, uintptr_t size, uintptr_t num, MonoObject **refs, uintptr_t *offsets, void *data)
 {
@@ -1048,13 +1082,16 @@ gc_resize (MonoProfiler *profiler, int64_t new_size) {
        EXIT_LOG (logbuffer);
 }
 
+// If you alter MAX_FRAMES, you may need to alter SAMPLE_BLOCK_SIZE too.
 #define MAX_FRAMES 32
+
 typedef struct {
        int count;
        MonoMethod* methods [MAX_FRAMES];
        int32_t il_offsets [MAX_FRAMES];
        int32_t native_offsets [MAX_FRAMES];
 } FrameData;
+
 static int num_frames = MAX_FRAMES;
 
 static mono_bool
@@ -1093,7 +1130,7 @@ emit_bt (MonoProfiler *prof, LogBuffer *logbuffer, FrameData *data)
        emit_value (logbuffer, 0); /* flags */
        emit_value (logbuffer, data->count);
        //if (*p != data.count) {
-       //      printf ("bad num frames enc at %d: %d -> %d\n", count, data.count, *p); printf ("frames end: %p->%p\n", p, logbuffer->data); exit(0);}
+       //      printf ("bad num frames enc at %d: %d -> %d\n", count, data.count, *p); printf ("frames end: %p->%p\n", p, logbuffer->cursor); exit(0);}
        while (data->count) {
                emit_method_as_ptr (prof, logbuffer, data->methods [--data->count]);
        }
@@ -1306,13 +1343,15 @@ image_loaded (MonoProfiler *prof, MonoImage *image, int result)
        emit_byte (logbuffer, TYPE_IMAGE);
        emit_ptr (logbuffer, image);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        //printf ("loaded image %p (%s)\n", image, name);
        EXIT_LOG (logbuffer);
        if (logbuffer->next)
                safe_send (prof, logbuffer);
        process_requests (prof);
+
+       InterlockedIncrement (&image_loads);
 }
 
 static void
@@ -1336,14 +1375,16 @@ image_unloaded (MonoProfiler *prof, MonoImage *image)
        emit_byte (logbuffer, TYPE_IMAGE);
        emit_ptr (logbuffer, image);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        EXIT_LOG (logbuffer);
 
        if (logbuffer->next)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&image_unloads);
 }
 
 static void
@@ -1370,8 +1411,8 @@ assembly_loaded (MonoProfiler *prof, MonoAssembly *assembly, int result)
        emit_byte (logbuffer, TYPE_ASSEMBLY);
        emit_ptr (logbuffer, assembly);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        EXIT_LOG (logbuffer);
 
        mono_free (name);
@@ -1380,6 +1421,8 @@ assembly_loaded (MonoProfiler *prof, MonoAssembly *assembly, int result)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&assembly_loads);
 }
 
 static void
@@ -1403,8 +1446,8 @@ assembly_unloaded (MonoProfiler *prof, MonoAssembly *assembly)
        emit_byte (logbuffer, TYPE_ASSEMBLY);
        emit_ptr (logbuffer, assembly);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        EXIT_LOG (logbuffer);
 
        mono_free (name);
@@ -1413,6 +1456,8 @@ assembly_unloaded (MonoProfiler *prof, MonoAssembly *assembly)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&assembly_unloads);
 }
 
 static void
@@ -1448,8 +1493,8 @@ class_loaded (MonoProfiler *prof, MonoClass *klass, int result)
        emit_ptr (logbuffer, klass);
        emit_ptr (logbuffer, image);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        //printf ("loaded class %p (%s)\n", klass, name);
        if (runtime_inited)
                mono_free (name);
@@ -1459,6 +1504,8 @@ class_loaded (MonoProfiler *prof, MonoClass *klass, int result)
        if (logbuffer->next)
                safe_send (prof, logbuffer);
        process_requests (prof);
+
+       InterlockedIncrement (&class_loads);
 }
 
 static void
@@ -1491,8 +1538,8 @@ class_unloaded (MonoProfiler *prof, MonoClass *klass)
        emit_ptr (logbuffer, klass);
        emit_ptr (logbuffer, image);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        EXIT_LOG (logbuffer);
 
        if (runtime_inited)
@@ -1504,6 +1551,8 @@ class_unloaded (MonoProfiler *prof, MonoClass *klass)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&class_unloads);
 }
 
 #ifndef DISABLE_HELPER_THREAD
@@ -1623,8 +1672,8 @@ code_buffer_new (MonoProfiler *prof, void *buffer, int size, MonoProfilerCodeBuf
        emit_ptr (logbuffer, buffer);
        emit_value (logbuffer, size);
        if (name) {
-               memcpy (logbuffer->data, name, nlen);
-               logbuffer->data += nlen;
+               memcpy (logbuffer->cursor, name, nlen);
+               logbuffer->cursor += nlen;
        }
        EXIT_LOG (logbuffer);
        process_requests (prof);
@@ -1744,6 +1793,8 @@ thread_start (MonoProfiler *prof, uintptr_t tid)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&thread_starts);
 }
 
 static void
@@ -1774,6 +1825,8 @@ thread_end (MonoProfiler *prof, uintptr_t tid)
 
        TLS_SET (tlsbuffer, NULL);
        TLS_SET (tlsmethodlist, NULL);
+
+       InterlockedIncrement (&thread_ends);
 }
 
 static void
@@ -1803,6 +1856,8 @@ domain_loaded (MonoProfiler *prof, MonoDomain *domain, int result)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&domain_loads);
 }
 
 static void
@@ -1829,6 +1884,8 @@ domain_unloaded (MonoProfiler *prof, MonoDomain *domain)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&domain_unloads);
 }
 
 static void
@@ -1851,8 +1908,8 @@ domain_name (MonoProfiler *prof, MonoDomain *domain, const char *name)
        emit_byte (logbuffer, TYPE_DOMAIN);
        emit_ptr (logbuffer, (void*)(uintptr_t) mono_domain_get_id (domain));
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, nlen);
-       logbuffer->data += nlen;
+       memcpy (logbuffer->cursor, name, nlen);
+       logbuffer->cursor += nlen;
        EXIT_LOG (logbuffer);
 
        if (logbuffer->next)
@@ -1887,6 +1944,8 @@ context_loaded (MonoProfiler *prof, MonoAppContext *context)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&context_loads);
 }
 
 static void
@@ -1915,6 +1974,8 @@ context_unloaded (MonoProfiler *prof, MonoAppContext *context)
                safe_send (prof, logbuffer);
 
        process_requests (prof);
+
+       InterlockedIncrement (&context_unloads);
 }
 
 static void
@@ -1938,8 +1999,8 @@ thread_name (MonoProfiler *prof, uintptr_t tid, const char *name)
        emit_byte (logbuffer, TYPE_THREAD);
        emit_ptr (logbuffer, (void*)tid);
        emit_value (logbuffer, 0); /* flags */
-       memcpy (logbuffer->data, name, len);
-       logbuffer->data += len;
+       memcpy (logbuffer->cursor, name, len);
+       logbuffer->cursor += len;
        EXIT_LOG (logbuffer);
 
        if (logbuffer->next)
@@ -1956,100 +2017,102 @@ typedef struct {
 } AsyncFrameInfo;
 
 typedef struct {
+       MonoLockFreeQueueNode node;
+       MonoProfiler *prof;
+       uint64_t elapsed;
+       uintptr_t tid;
+       void *ip;
        int count;
-       AsyncFrameInfo *data;
-} AsyncFrameData;
+       AsyncFrameInfo frames [MONO_ZERO_LEN_ARRAY];
+} SampleHit;
 
 static mono_bool
 async_walk_stack (MonoMethod *method, MonoDomain *domain, void *base_address, int offset, void *data)
 {
-       AsyncFrameData *frame = (AsyncFrameData *)data;
-       if (frame->count < num_frames) {
-               frame->data [frame->count].method = method;
-               frame->data [frame->count].domain = domain;
-               frame->data [frame->count].base_address = base_address;
-               frame->data [frame->count].offset = offset;
-               // printf ("In %d at %p (dom %p) (native: %p)\n", frame->count, method, domain, base_address);
-               frame->count++;
+       SampleHit *sample = (SampleHit *) data;
+
+       if (sample->count < num_frames) {
+               int i = sample->count;
+
+               sample->frames [i].method = method;
+               sample->frames [i].domain = domain;
+               sample->frames [i].base_address = base_address;
+               sample->frames [i].offset = offset;
+
+               sample->count++;
        }
-       return frame->count == num_frames;
+
+       return sample->count == num_frames;
 }
 
-/*
-(type | frame count), tid, time, ip, [method, domain, base address, offset] * frames
-*/
-#define SAMPLE_EVENT_SIZE_IN_SLOTS(FRAMES) (4 + (FRAMES) * 4)
+#define SAMPLE_SLOT_SIZE(FRAMES) (sizeof (SampleHit) + sizeof (AsyncFrameInfo) * (FRAMES - MONO_ZERO_LEN_ARRAY))
+#define SAMPLE_BLOCK_SIZE (mono_pagesize ())
+
+static void
+enqueue_sample_hit (gpointer p)
+{
+       SampleHit *sample = p;
+
+       mono_lock_free_queue_node_unpoison (&sample->node);
+       mono_lock_free_queue_enqueue (&sample->prof->dumper_queue, &sample->node);
+       mono_os_sem_post (&sample->prof->dumper_queue_sem);
+
+       InterlockedIncrement (&sample_flushes);
+}
 
 static void
 mono_sample_hit (MonoProfiler *profiler, unsigned char *ip, void *context)
 {
-       StatBuffer *sbuf;
-       AsyncFrameInfo frames [num_frames];
-       AsyncFrameData bt_data = { 0, &frames [0]};
-       uint64_t now;
-       uintptr_t *data, *new_data, *old_data;
-       uintptr_t elapsed;
-       int timedout = 0;
-       int i;
+       /*
+        * Please note: We rely on the runtime loading the profiler with
+        * MONO_DL_EAGER (RTLD_NOW) so that references to runtime functions within
+        * this function (and its siblings) are resolved when the profiler is
+        * loaded. Otherwise, we would potentially invoke the dynamic linker when
+        * invoking runtime functions, which is not async-signal-safe.
+        */
+
        if (in_shutdown)
                return;
-       now = current_time ();
 
-       mono_stack_walk_async_safe (&async_walk_stack, context, &bt_data);
+       InterlockedIncrement (&sample_hits);
+
+       uint64_t now = current_time ();
+
+       SampleHit *sample = (SampleHit *) mono_lock_free_queue_dequeue (&profiler->sample_reuse_queue);
+
+       if (!sample) {
+               /*
+                * If we're out of reusable sample events and we're not allowed to
+                * allocate more, we have no choice but to drop the event.
+                */
+               if (InterlockedRead (&sample_allocations) >= max_allocated_sample_hits)
+                       return;
+
+               sample = mono_lock_free_alloc (&profiler->sample_allocator);
+               sample->prof = profiler;
+               mono_lock_free_queue_node_init (&sample->node, TRUE);
+
+               InterlockedIncrement (&sample_allocations);
+       }
+
+       sample->count = 0;
+       mono_stack_walk_async_safe (&async_walk_stack, context, sample);
+
+       uintptr_t elapsed = (now - profiler->startup_time) / 10000;
+
+       sample->elapsed = elapsed;
+       sample->tid = thread_id ();
+       sample->ip = ip;
 
-       elapsed = (now - profiler->startup_time) / 10000;
        if (do_debug) {
                int len;
                char buf [256];
-               snprintf (buf, sizeof (buf), "hit at %p in thread %p after %llu ms\n", ip, (void*)thread_id (), (unsigned long long int)elapsed/100);
+               snprintf (buf, sizeof (buf), "hit at %p in thread %p after %llu ms\n", ip, (void *) thread_id (), (unsigned long long int) elapsed / 100);
                len = strlen (buf);
                ign_res (write (2, buf, len));
        }
-       sbuf = profiler->stat_buffers;
-       if (!sbuf)
-               return;
-       /* flush the buffer at 1 second intervals */
-       if (sbuf->data > sbuf->buf && (elapsed - sbuf->buf [2]) > 100000) {
-               timedout = 1;
-       }
-       /* overflow: 400 slots is a big enough number to reduce the chance of losing this event if many
-        * threads hit this same spot at the same time
-        */
-       if (timedout || (sbuf->data + 400 >= sbuf->data_end)) {
-               StatBuffer *oldsb, *foundsb;
-               sbuf = create_stat_buffer ();
-               do {
-                       oldsb = profiler->stat_buffers;
-                       sbuf->next = oldsb;
-                       foundsb = (StatBuffer *)InterlockedCompareExchangePointer ((void * volatile*)&profiler->stat_buffers, sbuf, oldsb);
-               } while (foundsb != oldsb);
-               if (do_debug)
-                       ign_res (write (2, "overflow\n", 9));
-               /* notify the helper thread */
-               if (sbuf->next->next) {
-                       char c = 0;
-                       ign_res (write (profiler->pipes [1], &c, 1));
-                       if (do_debug)
-                               ign_res (write (2, "notify\n", 7));
-               }
-       }
-       do {
-               old_data = sbuf->data;
-               new_data = old_data + SAMPLE_EVENT_SIZE_IN_SLOTS (bt_data.count);
-               data = (uintptr_t *)InterlockedCompareExchangePointer ((void * volatile*)&sbuf->data, new_data, old_data);
-       } while (data != old_data);
-       if (old_data >= sbuf->data_end)
-               return; /* lost event */
-       old_data [0] = 1 | (sample_type << 16) | (bt_data.count << 8);
-       old_data [1] = thread_id ();
-       old_data [2] = elapsed;
-       old_data [3] = (uintptr_t)ip;
-       for (i = 0; i < bt_data.count; ++i) {
-               old_data [4 + 4 * i + 0] = (uintptr_t)frames [i].method;
-               old_data [4 + 4 * i + 1] = (uintptr_t)frames [i].domain;
-               old_data [4 + 4 * i + 2] = (uintptr_t)frames [i].base_address;
-               old_data [4 + 4 * i + 3] = (uintptr_t)frames [i].offset;
-       }
+
+       mono_thread_hazardous_try_free (sample, enqueue_sample_hit);
 }
 
 static uintptr_t *code_pages = 0;
@@ -2129,8 +2192,8 @@ dump_ubin (const char *filename, uintptr_t load_addr, uint64_t offset, uintptr_t
        emit_svalue (logbuffer, load_addr);
        emit_uvalue (logbuffer, offset);
        emit_uvalue (logbuffer, size);
-       memcpy (logbuffer->data, filename, len);
-       logbuffer->data += len;
+       memcpy (logbuffer->cursor, filename, len);
+       logbuffer->cursor += len;
 }
 #endif
 
@@ -2149,8 +2212,8 @@ dump_usym (const char *name, uintptr_t value, uintptr_t size)
        emit_byte (logbuffer, TYPE_SAMPLE | TYPE_SAMPLE_USYM);
        emit_ptr (logbuffer, (void*)value);
        emit_value (logbuffer, size);
-       memcpy (logbuffer->data, name, len);
-       logbuffer->data += len;
+       memcpy (logbuffer->cursor, name, len);
+       logbuffer->cursor += len;
 }
 
 /* ELF code crashes on some systems. */
@@ -2389,110 +2452,6 @@ dump_unmanaged_coderefs (MonoProfiler *prof)
        }
 }
 
-static gint
-compare_sample_events (gconstpointer a, gconstpointer b)
-{
-       uintptr_t tid1 = (*(uintptr_t **) a) [1];
-       uintptr_t tid2 = (*(uintptr_t **) b) [1];
-
-       return tid1 > tid2 ? 1 :
-              tid1 < tid2 ? -1 :
-              0;
-}
-
-static void
-dump_sample_hits (MonoProfiler *prof, StatBuffer *sbuf)
-{
-       LogBuffer *logbuffer;
-       if (!sbuf)
-               return;
-       if (sbuf->next) {
-               dump_sample_hits (prof, sbuf->next);
-               free_buffer (sbuf->next, sbuf->next->size);
-               sbuf->next = NULL;
-       }
-
-       g_ptr_array_set_size (prof->sorted_sample_events, 0);
-
-       for (uintptr_t *sample = sbuf->buf; sample < sbuf->data;) {
-               int count = sample [0] & 0xff;
-               int mbt_count = (sample [0] & 0xff00) >> 8;
-
-               if (sample + SAMPLE_EVENT_SIZE_IN_SLOTS (mbt_count) > sbuf->data)
-                       break;
-
-               g_ptr_array_add (prof->sorted_sample_events, sample);
-
-               sample += count + 3 + 4 * mbt_count;
-       }
-
-       g_ptr_array_sort (prof->sorted_sample_events, compare_sample_events);
-
-       for (guint sidx = 0; sidx < prof->sorted_sample_events->len; sidx++) {
-               uintptr_t *sample = (uintptr_t *)g_ptr_array_index (prof->sorted_sample_events, sidx);
-               int count = sample [0] & 0xff;
-               int mbt_count = (sample [0] & 0xff00) >> 8;
-               int type = sample [0] >> 16;
-               uintptr_t *managed_sample_base = sample + count + 3;
-               uintptr_t thread_id = sample [1];
-
-               for (int i = 0; i < mbt_count; ++i) {
-                       MonoMethod *method = (MonoMethod*)managed_sample_base [i * 4 + 0];
-                       MonoDomain *domain = (MonoDomain*)managed_sample_base [i * 4 + 1];
-                       void *address = (void*)managed_sample_base [i * 4 + 2];
-
-                       if (!method) {
-                               MonoJitInfo *ji = mono_jit_info_table_find (domain, (char *)address);
-
-                               if (ji)
-                                       managed_sample_base [i * 4 + 0] = (uintptr_t)mono_jit_info_get_method (ji);
-                       }
-               }
-
-               logbuffer = ensure_logbuf (
-                       EVENT_SIZE /* event */ +
-                       LEB128_SIZE /* type */ +
-                       LEB128_SIZE /* time */ +
-                       LEB128_SIZE /* tid */ +
-                       LEB128_SIZE /* count */ +
-                       count * (
-                               LEB128_SIZE /* ip */
-                       ) +
-                       LEB128_SIZE /* managed count */ +
-                       mbt_count * (
-                               LEB128_SIZE /* method */ +
-                               LEB128_SIZE /* il offset */ +
-                               LEB128_SIZE /* native offset */
-                       )
-               );
-               emit_byte (logbuffer, TYPE_SAMPLE | TYPE_SAMPLE_HIT);
-               emit_value (logbuffer, type);
-               emit_uvalue (logbuffer, prof->startup_time + (uint64_t)sample [2] * (uint64_t)10000);
-               emit_ptr (logbuffer, (void *) thread_id);
-               emit_value (logbuffer, count);
-               for (int i = 0; i < count; ++i) {
-                       emit_ptr (logbuffer, (void*)sample [i + 3]);
-                       add_code_pointer (sample [i + 3]);
-               }
-
-               sample += count + 3;
-               /* new in data version 6 */
-               emit_uvalue (logbuffer, mbt_count);
-               for (int i = 0; i < mbt_count; ++i) {
-                       MonoMethod *method = (MonoMethod *) sample [i * 4 + 0];
-                       uintptr_t native_offset = sample [i * 4 + 3];
-
-                       emit_method (prof, logbuffer, method);
-                       emit_svalue (logbuffer, 0); /* il offset will always be 0 from now on */
-                       emit_svalue (logbuffer, native_offset);
-               }
-       }
-
-       dump_unmanaged_coderefs (prof);
-}
-
-#if USE_PERF_EVENTS
-
 static int
 mono_cpu_count (void)
 {
@@ -2571,6 +2530,8 @@ mono_cpu_count (void)
        return 1;
 }
 
+#if USE_PERF_EVENTS
+
 typedef struct {
        int perf_fd;
        unsigned int prev_pos;
@@ -2869,7 +2830,7 @@ counters_init (MonoProfiler *profiler)
 }
 
 static void
-counters_emit (MonoProfiler *profiler)
+counters_emit (MonoProfiler *profiler, gboolean threadless)
 {
        MonoCounterAgent *agent;
        LogBuffer *logbuffer;
@@ -2928,13 +2889,16 @@ counters_emit (MonoProfiler *profiler)
        }
        EXIT_LOG (logbuffer);
 
-       safe_send (profiler, logbuffer);
+       if (threadless)
+               safe_send_threadless (profiler, logbuffer);
+       else
+               safe_send (profiler, logbuffer);
 
        mono_os_mutex_unlock (&counters_mutex);
 }
 
 static void
-counters_sample (MonoProfiler *profiler, uint64_t timestamp)
+counters_sample (MonoProfiler *profiler, uint64_t timestamp, gboolean threadless)
 {
        MonoCounterAgent *agent;
        MonoCounter *counter;
@@ -2947,7 +2911,7 @@ counters_sample (MonoProfiler *profiler, uint64_t timestamp)
        if (!counters_initialized)
                return;
 
-       counters_emit (profiler);
+       counters_emit (profiler, threadless);
 
        buffer_size = 8;
        buffer = calloc (1, buffer_size);
@@ -3059,7 +3023,10 @@ counters_sample (MonoProfiler *profiler, uint64_t timestamp)
        emit_value (logbuffer, 0);
        EXIT_LOG (logbuffer);
 
-       safe_send (profiler, logbuffer);
+       if (threadless)
+               safe_send_threadless (profiler, logbuffer);
+       else
+               safe_send (profiler, logbuffer);
 
        mono_os_mutex_unlock (&counters_mutex);
 }
@@ -3080,7 +3047,7 @@ struct _PerfCounterAgent {
 static PerfCounterAgent *perfcounters = NULL;
 
 static void
-perfcounters_emit (MonoProfiler *profiler)
+perfcounters_emit (MonoProfiler *profiler, gboolean threadless)
 {
        PerfCounterAgent *pcagent;
        LogBuffer *logbuffer;
@@ -3131,7 +3098,10 @@ perfcounters_emit (MonoProfiler *profiler)
        }
        EXIT_LOG (logbuffer);
 
-       safe_send (profiler, logbuffer);
+       if (threadless)
+               safe_send_threadless (profiler, logbuffer);
+       else
+               safe_send (profiler, logbuffer);
 }
 
 static gboolean
@@ -3168,7 +3138,7 @@ perfcounters_foreach (char *category_name, char *name, unsigned char type, gint6
 }
 
 static void
-perfcounters_sample (MonoProfiler *profiler, uint64_t timestamp)
+perfcounters_sample (MonoProfiler *profiler, uint64_t timestamp, gboolean threadless)
 {
        PerfCounterAgent *pcagent;
        LogBuffer *logbuffer;
@@ -3185,7 +3155,7 @@ perfcounters_sample (MonoProfiler *profiler, uint64_t timestamp)
 
        mono_perfcounter_foreach (perfcounters_foreach, perfcounters);
 
-       perfcounters_emit (profiler);
+       perfcounters_emit (profiler, threadless);
 
        size =
                EVENT_SIZE /* event */ +
@@ -3225,13 +3195,16 @@ perfcounters_sample (MonoProfiler *profiler, uint64_t timestamp)
        emit_value (logbuffer, 0);
        EXIT_LOG (logbuffer);
 
-       safe_send (profiler, logbuffer);
+       if (threadless)
+               safe_send_threadless (profiler, logbuffer);
+       else
+               safe_send (profiler, logbuffer);
 
        mono_os_mutex_unlock (&counters_mutex);
 }
 
 static void
-counters_and_perfcounters_sample (MonoProfiler *prof)
+counters_and_perfcounters_sample (MonoProfiler *prof, gboolean threadless)
 {
        static uint64_t start = -1;
        uint64_t now;
@@ -3240,8 +3213,8 @@ counters_and_perfcounters_sample (MonoProfiler *prof)
                start = current_time ();
 
        now = current_time ();
-       counters_sample (prof, (now - start) / 1000/ 1000);
-       perfcounters_sample (prof, (now - start) / 1000/ 1000);
+       counters_sample (prof, (now - start) / 1000/ 1000, threadless);
+       perfcounters_sample (prof, (now - start) / 1000/ 1000, threadless);
 }
 
 #define COVERAGE_DEBUG(x) if (debug_coverage) {x}
@@ -3451,7 +3424,7 @@ count_queue (MonoLockFreeQueue *queue)
 
        while ((node = mono_lock_free_queue_dequeue (queue))) {
                count++;
-               mono_lock_free_queue_node_free (node);
+               mono_thread_hazardous_try_free (node, free);
        }
 
        return count;
@@ -3731,6 +3704,11 @@ coverage_filter (MonoProfiler *prof, MonoMethod *method)
 
        assembly = mono_image_get_assembly (image);
 
+       // Need to keep the assemblies around for as long as they are kept in the hashtable
+       // Nunit, for example, has a habit of unloading them before the coverage statistics are
+       // generated causing a crash. See https://bugzilla.xamarin.com/show_bug.cgi?id=39325
+       mono_assembly_addref (assembly);
+
        mono_os_mutex_lock (&coverage_mutex);
        mono_conc_hashtable_insert (coverage_methods, method, method);
        mono_conc_hashtable_insert (coverage_assemblies, assembly, assembly);
@@ -3872,6 +3850,28 @@ coverage_init (MonoProfiler *prof)
 #endif /* DISABLE_HELPER_THREAD */
 }
 
+static void
+unref_coverage_assemblies (gpointer key, gpointer value, gpointer userdata)
+{
+       MonoAssembly *assembly = (MonoAssembly *)value;
+       mono_assembly_close (assembly);
+}
+
+static void
+free_sample_hit (gpointer p)
+{
+       mono_lock_free_free (p, SAMPLE_BLOCK_SIZE);
+}
+
+static void
+cleanup_reusable_samples (MonoProfiler *prof)
+{
+       SampleHit *sample;
+
+       while ((sample = (SampleHit *) mono_lock_free_queue_dequeue (&prof->sample_reuse_queue)))
+               mono_thread_hazardous_try_free (sample, free_sample_hit);
+}
+
 static void
 log_shutdown (MonoProfiler *prof)
 {
@@ -3879,7 +3879,7 @@ log_shutdown (MonoProfiler *prof)
 
        in_shutdown = 1;
 #ifndef DISABLE_HELPER_THREAD
-       counters_and_perfcounters_sample (prof);
+       counters_and_perfcounters_sample (prof, FALSE);
 
        dump_coverage (prof);
 
@@ -3897,16 +3897,23 @@ log_shutdown (MonoProfiler *prof)
        }
 #endif
 
-       g_ptr_array_free (prof->sorted_sample_events, TRUE);
-
        if (TLS_GET (LogBuffer, tlsbuffer))
                send_buffer (prof, TLS_GET (GPtrArray, tlsmethodlist), TLS_GET (LogBuffer, tlsbuffer));
 
        TLS_SET (tlsbuffer, NULL);
        TLS_SET (tlsmethodlist, NULL);
 
+       InterlockedWrite (&prof->run_dumper_thread, 0);
+       mono_os_sem_post (&prof->dumper_queue_sem);
+       pthread_join (prof->dumper_thread, &res);
+       mono_os_sem_destroy (&prof->dumper_queue_sem);
+
        InterlockedWrite (&prof->run_writer_thread, 0);
+       mono_os_sem_post (&prof->writer_queue_sem);
        pthread_join (prof->writer_thread, &res);
+       mono_os_sem_destroy (&prof->writer_queue_sem);
+
+       cleanup_reusable_samples (prof);
 
 #if defined (HAVE_SYS_ZLIB)
        if (prof->gzfile)
@@ -3921,6 +3928,10 @@ log_shutdown (MonoProfiler *prof)
        mono_os_mutex_destroy (&prof->method_table_mutex);
 
        if (coverage_initialized) {
+               mono_os_mutex_lock (&coverage_mutex);
+               mono_conc_hashtable_foreach (coverage_assemblies, unref_coverage_assemblies, prof);
+               mono_os_mutex_unlock (&coverage_mutex);
+
                mono_conc_hashtable_destroy (coverage_methods);
                mono_conc_hashtable_destroy (coverage_assemblies);
                mono_conc_hashtable_destroy (coverage_classes);
@@ -4009,6 +4020,8 @@ helper_thread (void* arg)
        MonoThread *thread = NULL;
 
        mono_threads_attach_tools_thread ();
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Profiler helper");
+
        //fprintf (stderr, "Server listening\n");
        command_socket = -1;
        while (1) {
@@ -4039,7 +4052,7 @@ helper_thread (void* arg)
                }
 #endif
 
-               counters_and_perfcounters_sample (prof);
+               counters_and_perfcounters_sample (prof, TRUE);
 
                tv.tv_sec = 1;
                tv.tv_usec = 0;
@@ -4055,25 +4068,7 @@ helper_thread (void* arg)
 
                if (FD_ISSET (prof->pipes [0], &rfds)) {
                        char c;
-                       int r = read (prof->pipes [0], &c, 1);
-                       if (r == 1 && c == 0) {
-                               StatBuffer *sbufbase = prof->stat_buffers;
-                               StatBuffer *sbuf;
-                               if (!sbufbase->next)
-                                       continue;
-                               sbuf = sbufbase->next->next;
-                               sbufbase->next->next = NULL;
-                               if (do_debug)
-                                       fprintf (stderr, "stat buffer dump\n");
-                               if (sbuf) {
-                                       dump_sample_hits (prof, sbuf);
-                                       free_buffer (sbuf, sbuf->size);
-                                       safe_send (prof, ensure_logbuf (0));
-                               }
-                               continue;
-                       }
-                       /* time to shut down */
-                       dump_sample_hits (prof, prof->stat_buffers);
+                       read (prof->pipes [0], &c, 1);
                        if (thread)
                                mono_thread_detach (thread);
                        if (do_debug)
@@ -4089,7 +4084,7 @@ helper_thread (void* arg)
                                }
                        }
 #endif
-                       safe_send (prof, ensure_logbuf (0));
+                       safe_send_threadless (prof, ensure_logbuf (0));
                        return NULL;
                }
 #if USE_PERF_EVENTS
@@ -4100,7 +4095,7 @@ helper_thread (void* arg)
                                        continue;
                                if (FD_ISSET (perf_data [i].perf_fd, &rfds)) {
                                        read_perf_mmap (prof, i);
-                                       safe_send (prof, ensure_logbuf (0));
+                                       safe_send_threadless (prof, ensure_logbuf (0));
                                }
                        }
                }
@@ -4138,6 +4133,9 @@ helper_thread (void* arg)
                        continue;
                //fprintf (stderr, "Accepted connection\n");
        }
+
+       mono_thread_info_detach ();
+
        return NULL;
 }
 
@@ -4185,101 +4183,232 @@ start_helper_thread (MonoProfiler* prof)
 }
 #endif
 
+static gboolean
+handle_writer_queue_entry (MonoProfiler *prof)
+{
+       WriterQueueEntry *entry;
+
+       if ((entry = (WriterQueueEntry *) mono_lock_free_queue_dequeue (&prof->writer_queue))) {
+               LogBuffer *method_buffer = NULL;
+               gboolean new_methods = FALSE;
+
+               if (entry->methods->len)
+                       method_buffer = create_buffer ();
+
+               /*
+                * Encode the method events in a temporary log buffer that we
+                * flush to disk before the main buffer, ensuring that all
+                * methods have metadata emitted before they're referenced.
+                */
+               for (guint i = 0; i < entry->methods->len; i++) {
+                       MethodInfo *info = (MethodInfo *)g_ptr_array_index (entry->methods, i);
+
+                       if (mono_conc_hashtable_lookup (prof->method_table, info->method))
+                               continue;
+
+                       new_methods = TRUE;
+
+                       /*
+                        * Other threads use this hash table to get a general
+                        * idea of whether a method has already been emitted to
+                        * the stream. Due to the way we add to this table, it
+                        * can easily happen that multiple threads queue up the
+                        * same methods, but that's OK since eventually all
+                        * methods will be in this table and the thread-local
+                        * method lists will just be empty for the rest of the
+                        * app's lifetime.
+                        */
+                       mono_os_mutex_lock (&prof->method_table_mutex);
+                       mono_conc_hashtable_insert (prof->method_table, info->method, info->method);
+                       mono_os_mutex_unlock (&prof->method_table_mutex);
+
+                       char *name = mono_method_full_name (info->method, 1);
+                       int nlen = strlen (name) + 1;
+                       void *cstart = info->ji ? mono_jit_info_get_code_start (info->ji) : NULL;
+                       int csize = info->ji ? mono_jit_info_get_code_size (info->ji) : 0;
+
+                       method_buffer = ensure_logbuf_inner (method_buffer,
+                               EVENT_SIZE /* event */ +
+                               LEB128_SIZE /* time */ +
+                               LEB128_SIZE /* method */ +
+                               LEB128_SIZE /* start */ +
+                               LEB128_SIZE /* size */ +
+                               nlen /* name */
+                       );
+
+                       emit_byte (method_buffer, TYPE_JIT | TYPE_METHOD);
+                       emit_time (method_buffer, info->time);
+                       emit_method_inner (method_buffer, info->method);
+                       emit_ptr (method_buffer, cstart);
+                       emit_value (method_buffer, csize);
+
+                       memcpy (method_buffer->cursor, name, nlen);
+                       method_buffer->cursor += nlen;
+
+                       mono_free (name);
+                       free (info);
+               }
+
+               g_ptr_array_free (entry->methods, TRUE);
+
+               if (new_methods) {
+                       for (LogBuffer *iter = method_buffer; iter; iter = iter->next)
+                               iter->thread_id = 0;
+
+                       dump_buffer (prof, method_buffer);
+               } else if (method_buffer)
+                       free_buffer (method_buffer, method_buffer->size);
+
+               dump_buffer (prof, entry->buffer);
+
+               mono_thread_hazardous_try_free (entry, free);
+
+               return TRUE;
+       }
+
+       return FALSE;
+}
+
 static void *
 writer_thread (void *arg)
 {
        MonoProfiler *prof = (MonoProfiler *)arg;
 
        mono_threads_attach_tools_thread ();
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Profiler writer");
 
        dump_header (prof);
 
        while (InterlockedRead (&prof->run_writer_thread)) {
-               WriterQueueEntry *entry;
+               mono_os_sem_wait (&prof->writer_queue_sem, MONO_SEM_FLAGS_NONE);
+               handle_writer_queue_entry (prof);
+       }
 
-               while ((entry = (WriterQueueEntry *) mono_lock_free_queue_dequeue (&prof->writer_queue))) {
-                       LogBuffer *method_buffer = NULL;
-                       gboolean new_methods = FALSE;
+       /* Drain any remaining entries on shutdown. */
+       while (handle_writer_queue_entry (prof));
 
-                       if (entry->methods->len)
-                               method_buffer = create_buffer ();
+       mono_thread_info_detach ();
 
-                       /*
-                        * Encode the method events in a temporary log buffer that we
-                        * flush to disk before the main buffer, ensuring that all
-                        * methods have metadata emitted before they're referenced.
-                        */
-                       for (guint i = 0; i < entry->methods->len; i++) {
-                               MethodInfo *info = (MethodInfo *)g_ptr_array_index (entry->methods, i);
+       return NULL;
+}
 
-                               if (mono_conc_hashtable_lookup (prof->method_table, info->method))
-                                       continue;
+static int
+start_writer_thread (MonoProfiler* prof)
+{
+       InterlockedWrite (&prof->run_writer_thread, 1);
+
+       return !pthread_create (&prof->writer_thread, NULL, writer_thread, prof);
+}
+
+static void
+reuse_sample_hit (gpointer p)
+{
+       SampleHit *sample = p;
+
+       mono_lock_free_queue_node_unpoison (&sample->node);
+       mono_lock_free_queue_enqueue (&sample->prof->sample_reuse_queue, &sample->node);
+}
+
+static gboolean
+handle_dumper_queue_entry (MonoProfiler *prof)
+{
+       SampleHit *sample;
+
+       if ((sample = (SampleHit *) mono_lock_free_queue_dequeue (&prof->dumper_queue))) {
+               for (int i = 0; i < sample->count; ++i) {
+                       MonoMethod *method = sample->frames [i].method;
+                       MonoDomain *domain = sample->frames [i].domain;
+                       void *address = sample->frames [i].base_address;
+
+                       if (!method) {
+                               g_assert (domain);
+                               g_assert (address);
+
+                               MonoJitInfo *ji = mono_jit_info_table_find (domain, (char *) address);
 
-                               new_methods = TRUE;
-
-                               /*
-                                * Other threads use this hash table to get a general
-                                * idea of whether a method has already been emitted to
-                                * the stream. Due to the way we add to this table, it
-                                * can easily happen that multiple threads queue up the
-                                * same methods, but that's OK since eventually all
-                                * methods will be in this table and the thread-local
-                                * method lists will just be empty for the rest of the
-                                * app's lifetime.
-                                */
-                               mono_os_mutex_lock (&prof->method_table_mutex);
-                               mono_conc_hashtable_insert (prof->method_table, info->method, info->method);
-                               mono_os_mutex_unlock (&prof->method_table_mutex);
-
-                               char *name = mono_method_full_name (info->method, 1);
-                               int nlen = strlen (name) + 1;
-                               void *cstart = info->ji ? mono_jit_info_get_code_start (info->ji) : NULL;
-                               int csize = info->ji ? mono_jit_info_get_code_size (info->ji) : 0;
-
-                               method_buffer = ensure_logbuf_inner (method_buffer,
-                                       EVENT_SIZE /* event */ +
-                                       LEB128_SIZE /* time */ +
-                                       LEB128_SIZE /* method */ +
-                                       LEB128_SIZE /* start */ +
-                                       LEB128_SIZE /* size */ +
-                                       nlen /* name */
-                               );
-
-                               emit_byte (method_buffer, TYPE_JIT | TYPE_METHOD);
-                               emit_time (method_buffer, info->time);
-                               emit_method_inner (method_buffer, info->method);
-                               emit_ptr (method_buffer, cstart);
-                               emit_value (method_buffer, csize);
-
-                               memcpy (method_buffer->data, name, nlen);
-                               method_buffer->data += nlen;
-
-                               mono_free (name);
-                               free (info);
+                               if (ji)
+                                       sample->frames [i].method = mono_jit_info_get_method (ji);
                        }
+               }
 
-                       g_ptr_array_free (entry->methods, TRUE);
+               LogBuffer *logbuffer = ensure_logbuf (
+                       EVENT_SIZE /* event */ +
+                       LEB128_SIZE /* type */ +
+                       LEB128_SIZE /* time */ +
+                       LEB128_SIZE /* tid */ +
+                       LEB128_SIZE /* count */ +
+                       1 * (
+                               LEB128_SIZE /* ip */
+                       ) +
+                       LEB128_SIZE /* managed count */ +
+                       sample->count * (
+                               LEB128_SIZE /* method */ +
+                               LEB128_SIZE /* il offset */ +
+                               LEB128_SIZE /* native offset */
+                       )
+               );
 
-                       if (new_methods)
-                               dump_buffer (prof, method_buffer);
-                       else if (method_buffer)
-                               free_buffer (method_buffer, method_buffer->size);
+               emit_byte (logbuffer, TYPE_SAMPLE | TYPE_SAMPLE_HIT);
+               emit_value (logbuffer, sample_type);
+               emit_uvalue (logbuffer, prof->startup_time + sample->elapsed * 10000);
+               emit_ptr (logbuffer, (void *) sample->tid);
+               emit_value (logbuffer, 1);
+
+               // TODO: Actual native unwinding.
+               for (int i = 0; i < 1; ++i) {
+                       emit_ptr (logbuffer, sample->ip);
+                       add_code_pointer ((uintptr_t) sample->ip);
+               }
 
-                       dump_buffer (prof, entry->buffer);
+               /* new in data version 6 */
+               emit_uvalue (logbuffer, sample->count);
 
-                       free (entry);
+               for (int i = 0; i < sample->count; ++i) {
+                       emit_method (prof, logbuffer, sample->frames [i].method);
+                       emit_svalue (logbuffer, 0); /* il offset will always be 0 from now on */
+                       emit_svalue (logbuffer, sample->frames [i].offset);
                }
+
+               mono_thread_hazardous_try_free (sample, reuse_sample_hit);
+
+               dump_unmanaged_coderefs (prof);
+
+               if (logbuffer->next)
+                       safe_send_threadless (prof, logbuffer);
+       }
+
+       return FALSE;
+}
+
+static void *
+dumper_thread (void *arg)
+{
+       MonoProfiler *prof = (MonoProfiler *)arg;
+
+       mono_threads_attach_tools_thread ();
+       mono_thread_info_set_name (mono_native_thread_id_get (), "Profiler dumper");
+
+       while (InterlockedRead (&prof->run_dumper_thread)) {
+               mono_os_sem_wait (&prof->dumper_queue_sem, MONO_SEM_FLAGS_NONE);
+               handle_dumper_queue_entry (prof);
        }
 
+       /* Drain any remaining entries on shutdown. */
+       while (handle_dumper_queue_entry (prof));
+
+       safe_send_threadless (prof, ensure_logbuf (0));
+
+       mono_thread_info_detach ();
+
        return NULL;
 }
 
 static int
-start_writer_thread (MonoProfiler* prof)
+start_dumper_thread (MonoProfiler* prof)
 {
-       InterlockedWrite (&prof->run_writer_thread, 1);
+       InterlockedWrite (&prof->run_dumper_thread, 1);
 
-       return !pthread_create (&prof->writer_thread, NULL, writer_thread, prof);
+       return !pthread_create (&prof->dumper_thread, NULL, dumper_thread, prof);
 }
 
 static void
@@ -4293,11 +4422,12 @@ runtime_initialized (MonoProfiler *profiler)
 #endif
 
        start_writer_thread (profiler);
+       start_dumper_thread (profiler);
 
        InterlockedWrite (&runtime_inited, 1);
 #ifndef DISABLE_HELPER_THREAD
        counters_init (profiler);
-       counters_sample (profiler, 0);
+       counters_sample (profiler, 0, FALSE);
 #endif
        /* ensure the main thread data and startup are available soon */
        safe_send (profiler, ensure_logbuf (0));
@@ -4360,14 +4490,23 @@ create_profiler (const char *filename, GPtrArray *filters)
        }
 #endif
        if (do_mono_sample) {
-               prof->stat_buffers = create_stat_buffer ();
                need_helper_thread = 1;
        }
        if (do_counters && !need_helper_thread) {
                need_helper_thread = 1;
        }
 
-       prof->sorted_sample_events = g_ptr_array_sized_new (BUFFER_SIZE / SAMPLE_EVENT_SIZE_IN_SLOTS (0));
+       /*
+        * If you hit this assert while increasing MAX_FRAMES, you need to increase
+        * SAMPLE_BLOCK_SIZE as well.
+        */
+       g_assert (SAMPLE_SLOT_SIZE (MAX_FRAMES) * 2 < LOCK_FREE_ALLOC_SB_USABLE_SIZE (SAMPLE_BLOCK_SIZE));
+
+       // FIXME: We should free this stuff too.
+       mono_lock_free_allocator_init_size_class (&prof->sample_size_class, SAMPLE_SLOT_SIZE (num_frames), SAMPLE_BLOCK_SIZE);
+       mono_lock_free_allocator_init_allocator (&prof->sample_allocator, &prof->sample_size_class);
+
+       mono_lock_free_queue_init (&prof->sample_reuse_queue);
 
 #ifdef DISABLE_HELPER_THREAD
        if (hs_mode_ondemand)
@@ -4379,6 +4518,11 @@ create_profiler (const char *filename, GPtrArray *filters)
 #endif
 
        mono_lock_free_queue_init (&prof->writer_queue);
+       mono_os_sem_init (&prof->writer_queue_sem, 0);
+
+       mono_lock_free_queue_init (&prof->dumper_queue);
+       mono_os_sem_init (&prof->dumper_queue_sem, 0);
+
        mono_os_mutex_init (&prof->method_table_mutex);
        prof->method_table = mono_conc_hashtable_new (NULL, NULL);
 
@@ -4402,7 +4546,7 @@ usage (int do_exit)
        printf ("\theapshot[=MODE]      record heap shot info (by default at each major collection)\n");
        printf ("\t                     MODE: every XXms milliseconds, every YYgc collections, ondemand\n");
        printf ("\tcounters             sample counters every 1s\n");
-       printf ("\tsample[=TYPE]        use statistical sampling mode (by default cycles/1000)\n");
+       printf ("\tsample[=TYPE]        use statistical sampling mode (by default cycles/100)\n");
        printf ("\t                     TYPE: cycles,instr,cacherefs,cachemiss,branches,branchmiss\n");
        printf ("\t                     TYPE can be followed by /FREQUENCY\n");
        printf ("\ttime=fast            use a faster (but more inaccurate) timer\n");
@@ -4487,7 +4631,7 @@ set_sample_mode (char* val, int allow_empty)
 #endif
        if (allow_empty && !val) {
                sample_type = SAMPLE_CYCLES;
-               sample_freq = 1000;
+               sample_freq = 100;
                return;
        }
        if (strcmp (val, "mono") == 0) {
@@ -4514,7 +4658,7 @@ set_sample_mode (char* val, int allow_empty)
        } else if (*maybe_freq != 0) {
                usage (1);
        } else {
-               sample_freq = 1000;
+               sample_freq = 100;
        }
        free (val);
 }
@@ -4583,6 +4727,25 @@ mono_profiler_startup (const char *desc)
                MONO_PROFILE_INS_COVERAGE|MONO_PROFILE_APPDOMAIN_EVENTS|MONO_PROFILE_CONTEXT_EVENTS|
                MONO_PROFILE_ASSEMBLY_EVENTS;
 
+       max_allocated_sample_hits = mono_cpu_count () * 1000;
+
+       mono_counters_register ("Sample hits", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &sample_hits);
+       mono_counters_register ("Sample flushes", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &sample_flushes);
+       mono_counters_register ("Sample events allocated", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &sample_allocations);
+       mono_counters_register ("Log buffers allocated", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &buffer_allocations);
+       mono_counters_register ("Thread start events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &thread_starts);
+       mono_counters_register ("Thread stop events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &thread_ends);
+       mono_counters_register ("Domain load events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &domain_loads);
+       mono_counters_register ("Domain unload events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &domain_unloads);
+       mono_counters_register ("Context load events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &context_loads);
+       mono_counters_register ("Context unload events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &context_unloads);
+       mono_counters_register ("Assembly load events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &assembly_loads);
+       mono_counters_register ("Assembly unload events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &assembly_unloads);
+       mono_counters_register ("Image load events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &image_loads);
+       mono_counters_register ("Image unload events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &image_unloads);
+       mono_counters_register ("Class load events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &class_loads);
+       mono_counters_register ("Class unload events", MONO_COUNTER_UINT | MONO_COUNTER_PROFILER | MONO_COUNTER_MONOTONIC, &class_unloads);
+
        p = desc;
        if (strncmp (p, "log", 3))
                usage (1);
@@ -4685,6 +4848,14 @@ mono_profiler_startup (const char *desc)
                        notraces = num_frames == 0;
                        continue;
                }
+               if ((opt = match_option (p, "maxsamples", &val)) != p) {
+                       char *end;
+                       max_allocated_sample_hits = strtoul (val, &end, 10);
+                       if (!max_allocated_sample_hits)
+                               max_allocated_sample_hits = G_MAXINT32;
+                       free (val);
+                       continue;
+               }
                if ((opt = match_option (p, "calldepth", &val)) != p) {
                        char *end;
                        max_call_depth = strtoul (val, &end, 10);
@@ -4761,6 +4932,7 @@ mono_profiler_startup (const char *desc)
        prof = create_profiler (filename, filters);
        if (!prof)
                return;
+
        init_thread ();
 
        mono_profiler_install (prof, log_shutdown);
@@ -4768,11 +4940,11 @@ mono_profiler_startup (const char *desc)
        mono_profiler_install_allocation (gc_alloc);
        mono_profiler_install_gc_moves (gc_moves);
        mono_profiler_install_gc_roots (gc_handle, gc_roots);
-       mono_profiler_install_appdomain (NULL, domain_loaded, NULL, domain_unloaded);
+       mono_profiler_install_appdomain (NULL, domain_loaded, domain_unloaded, NULL);
        mono_profiler_install_appdomain_name (domain_name);
        mono_profiler_install_context (context_loaded, context_unloaded);
-       mono_profiler_install_class (NULL, class_loaded, NULL, class_unloaded);
-       mono_profiler_install_module (NULL, image_loaded, NULL, image_unloaded);
+       mono_profiler_install_class (NULL, class_loaded, class_unloaded, NULL);
+       mono_profiler_install_module (NULL, image_loaded, image_unloaded, NULL);
        mono_profiler_install_assembly (NULL, assembly_loaded, assembly_unloaded, NULL);
        mono_profiler_install_thread (thread_start, thread_end);
        mono_profiler_install_thread_name (thread_name);
@@ -4787,7 +4959,7 @@ mono_profiler_startup (const char *desc)
 
        if (do_mono_sample && sample_type == SAMPLE_CYCLES && !only_counters) {
                events |= MONO_PROFILE_STATISTICAL;
-               mono_profiler_set_statistical_mode (sampling_mode, 1000000 / sample_freq);
+               mono_profiler_set_statistical_mode (sampling_mode, sample_freq);
                mono_profiler_install_statistical (mono_sample_hit);
        }
 
index f1c8af5bf8b3c384ae5e800d1da53535b22683bb..ecb0e43b82334160ce788b255733b12902fce6ae 100644 (file)
@@ -5,7 +5,7 @@
 #define LOG_HEADER_ID 0x4D505A01
 #define LOG_VERSION_MAJOR 0
 #define LOG_VERSION_MINOR 4
-#define LOG_DATA_VERSION 11
+#define LOG_DATA_VERSION 12
 /*
  * Changes in data versions:
  * version 2: added offsets in heap walk
@@ -26,6 +26,7 @@
                removed TYPE_LOAD_ERR flag (profiler never generated it, now removed from the format itself)
                added TYPE_GC_HANDLE_{CREATED,DESTROYED}_BT
                TYPE_JIT events are no longer guaranteed to have code start/size info (can be zero)
+ * version 12: added MONO_COUNTER_PROFILER
  */
 
 enum {
@@ -93,6 +94,8 @@ enum {
        TYPE_END
 };
 
+// Sampling sources
+// Unless you have compiled with --enable-perf-events, only SAMPLE_CYCLES is available
 enum {
        SAMPLE_CYCLES = 1,
        SAMPLE_INSTRUCTIONS,
index 2113c25135f27c8e49cc8fc81588968c34d601f4..e6323460651712aad82d05a0bb261ae9ba88f1e8 100755 (executable)
@@ -15,8 +15,6 @@ my $minibuilddir = $builddir . "/mono/mini";
 
 # Setup the execution environment
 # for the profiler module
-append_path ("LD_LIBRARY_PATH", $profbuilddir . "/.libs");
-append_path ("DYLD_LIBRARY_PATH", $profbuilddir . "/.libs");
 append_path ("DYLD_LIBRARY_PATH", $minibuilddir . "/.libs");
 # for mprof-report
 append_path ("PATH", $profbuilddir);
index 9266dee403c1d5f91a6182e89ae820fb85c70c25..753024dcf72963e30c7ebef03da79e54b7cdc7e0 100644 (file)
@@ -12,6 +12,7 @@
  *   Paolo Molaro (lupus@ximian.com)
  *
  * Copyright 2010 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "utils.h"
 #include <stdlib.h>
index 7816c06d9f962e2d37b8b94d3281168726b2e31f..6027f7839a7faebb48ac492b3b10b15966b7d38a 100644 (file)
@@ -43,7 +43,6 @@ monosgen_sources = \
        sgen-los.c \
        sgen-major-copy-object.h \
        sgen-marksweep-drain-gray-stack.h \
-       sgen-marksweep-scan-object-concurrent.h \
        sgen-marksweep.c \
        sgen-memory-governor.c \
        sgen-memory-governor.h \
@@ -55,6 +54,8 @@ monosgen_sources = \
        sgen-pinning.h \
        sgen-pointer-queue.c \
        sgen-pointer-queue.h \
+       sgen-array-list.h \
+       sgen-array-list.c \
        sgen-protocol-def.h \
        sgen-protocol.c \
        sgen-protocol.h \
index a609c69d86fdb5e8185662c48775eea22ce5bb87..9fe2f3ceeb4a62b9fc16be861e6d28179fcaac1c 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_METADATA_GCINTERNALAGNOSTIC_H__
index 9d3f45195e115047b8e3c303c5d0ec1d21fbce6b..2bc3214f143745d39b577525eea5a6bbc257bd66 100644 (file)
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index 5e349f8416ee22539b4e1eee99f7e4599765cbd8..c72ed326b00afbb28d565e48b113352bed1965d1 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGENARCHDEP_H__
 #define __MONO_SGENARCHDEP_H__
@@ -89,7 +78,7 @@
 
 /* MS_BLOCK_SIZE must be a multiple of the system pagesize, which for some
    architectures is 64k.  */
-#if defined(TARGET_POWERPC64)
+#if defined(TARGET_POWERPC) || defined(TARGET_POWERPC64)
 #define ARCH_MIN_MS_BLOCK_SIZE (64*1024)
 #define ARCH_MIN_MS_BLOCK_SIZE_SHIFT   16
 #endif
diff --git a/mono/sgen/sgen-array-list.c b/mono/sgen/sgen-array-list.c
new file mode 100644 (file)
index 0000000..f84868e
--- /dev/null
@@ -0,0 +1,187 @@
+/*
+ * sgen-array-list.c: A pointer array list that doesn't require reallocs
+ *
+ * Copyright (C) 2016 Xamarin Inc
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License 2.0 as published by the Free Software Foundation;
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License 2.0 along with this library; if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifdef HAVE_SGEN_GC
+
+#include <string.h>
+
+#include "mono/sgen/sgen-gc.h"
+#include "mono/sgen/sgen-array-list.h"
+
+static void
+sgen_array_list_grow (SgenArrayList *array, guint32 old_capacity)
+{
+       const guint32 new_bucket = sgen_array_list_index_bucket (old_capacity);
+       const guint32 growth = sgen_array_list_bucket_size (new_bucket);
+       const guint32 new_capacity = old_capacity + growth;
+       const guint32 new_bucket_size = sizeof (**array->entries) * growth;
+       gpointer *entries;
+       if (array->capacity >= new_capacity)
+               return;
+       if (array->mem_type != -1)
+               entries = (gpointer*) sgen_alloc_internal_dynamic (new_bucket_size, array->mem_type, TRUE);
+       else
+               entries = (gpointer*) g_malloc0 (new_bucket_size);
+       if (array->bucket_alloc_callback)
+               array->bucket_alloc_callback (entries, new_bucket_size, TRUE);
+       /*
+        * The zeroing of the newly allocated bucket must be complete before storing
+        * the new bucket pointer.
+        */
+       mono_memory_write_barrier ();
+       if (InterlockedCompareExchangePointer ((volatile gpointer *)&array->entries [new_bucket], entries, NULL) == NULL) {
+               /*
+                * It must not be the case that we succeeded in setting the bucket
+                * pointer, while someone else succeeded in changing the capacity.
+                */
+               if (InterlockedCompareExchange ((volatile gint32 *)&array->capacity, new_capacity, old_capacity) != old_capacity)
+                       g_assert_not_reached ();
+               array->slot_hint = old_capacity;
+               return;
+       }
+       /* Someone beat us to the allocation. */
+       if (array->bucket_alloc_callback)
+               array->bucket_alloc_callback (entries, new_bucket_size, FALSE);
+       if (array->mem_type != -1)
+               sgen_free_internal_dynamic (entries, new_bucket_size, array->mem_type);
+       else
+               g_free (entries);
+}
+
+static guint32
+sgen_array_list_find_unset (SgenArrayList *array, guint32 capacity)
+{
+       if (!array->is_slot_set_func) {
+               guint32 next_slot = array->next_slot;
+               /* We can't lookup empty slots, use next_slot */
+               if (next_slot < capacity)
+                       return next_slot;
+       } else {
+               guint32 slot_hint = array->slot_hint;
+               guint32 index;
+               volatile gpointer *slot;
+
+               SGEN_ARRAY_LIST_FOREACH_SLOT_RANGE(array, slot_hint, capacity, slot, index) {
+                       if (!array->is_slot_set_func (slot))
+                               return index;
+               } SGEN_ARRAY_LIST_END_FOREACH_SLOT_RANGE;
+
+               SGEN_ARRAY_LIST_FOREACH_SLOT_RANGE (array, 0, slot_hint, slot, index) {
+                       if (!array->is_slot_set_func (slot))
+                               return index;
+               } SGEN_ARRAY_LIST_END_FOREACH_SLOT_RANGE;
+       }
+
+       return -1;
+}
+
+static void
+sgen_array_list_update_next_slot (SgenArrayList *array, guint32 new_index)
+{
+       if (!array->set_slot_func) {
+               /*
+                * If we don't have a custom setter it means we don't have thread
+                * safety requirements.
+                */
+               if (new_index >= array->next_slot)
+                       array->next_slot = new_index + 1;
+       } else {
+               guint32 old_next_slot;
+               /* Thread safe update */
+               do {
+                       old_next_slot = array->next_slot;
+                       if (new_index < old_next_slot)
+                               break;
+               } while (InterlockedCompareExchange ((volatile gint32 *)&array->next_slot, new_index + 1, old_next_slot) != old_next_slot);
+       }
+}
+
+guint32
+sgen_array_list_add (SgenArrayList *array, gpointer ptr, int data, gboolean increase_size_before_set)
+{
+       guint32 index, capacity;
+       volatile gpointer *slot;
+
+       if (!array->capacity)
+               sgen_array_list_grow (array, 0);
+retry:
+       capacity = array->capacity;
+       index = sgen_array_list_find_unset (array, capacity);
+       if (index == -1) {
+               sgen_array_list_grow (array, capacity);
+               goto retry;
+       }
+       array->slot_hint = index;
+
+       if (increase_size_before_set) {
+               sgen_array_list_update_next_slot (array, index);
+               mono_memory_write_barrier ();
+       }
+
+       slot = sgen_array_list_get_slot (array, index);
+       if (array->set_slot_func) {
+               if (!array->set_slot_func (slot, ptr, data))
+                       goto retry;
+       } else {
+               *slot = ptr;
+       }
+
+       if (!increase_size_before_set) {
+               mono_memory_write_barrier ();
+               sgen_array_list_update_next_slot (array, index);
+       }
+
+       return index;
+}
+
+/*
+ * Removes all NULL pointers from the array. Not thread safe
+ */
+void
+sgen_array_list_remove_nulls (SgenArrayList *array)
+{
+       guint32 start = 0;
+       volatile gpointer *slot;
+
+       SGEN_ARRAY_LIST_FOREACH_SLOT (array, slot) {
+               if (*slot)
+                       *sgen_array_list_get_slot (array, start++) = *slot;
+       } SGEN_ARRAY_LIST_END_FOREACH_SLOT;
+
+       mono_memory_write_barrier ();
+       array->next_slot = start;
+}
+
+/*
+ * Does a linear search through the pointer array to find `ptr`.  Returns the index if
+ * found, otherwise (guint32)-1.
+ */
+guint32
+sgen_array_list_find (SgenArrayList *array, gpointer ptr)
+{
+       volatile gpointer *slot;
+
+       SGEN_ARRAY_LIST_FOREACH_SLOT (array, slot) {
+               if (*slot == ptr)
+                       return __index;
+       } SGEN_ARRAY_LIST_END_FOREACH_SLOT;
+       return (guint32)-1;
+}
+
+#endif
diff --git a/mono/sgen/sgen-array-list.h b/mono/sgen/sgen-array-list.h
new file mode 100644 (file)
index 0000000..fb37009
--- /dev/null
@@ -0,0 +1,136 @@
+/*
+ * sgen-array-list.h: A pointer array that doesn't use reallocs.
+ *
+ * Copyright (C) 2016 Xamarin Inc
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License 2.0 as published by the Free Software Foundation;
+ *
+ * This library 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
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public
+ * License 2.0 along with this library; if not, write to the Free
+ * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ */
+
+#ifndef __MONO_SGEN_ARRAY_LIST_H__
+#define __MONO_SGEN_ARRAY_LIST_H__
+
+#include <glib.h>
+
+#define SGEN_ARRAY_LIST_BUCKETS (32)
+#define SGEN_ARRAY_LIST_MIN_BUCKET_BITS (5)
+#define SGEN_ARRAY_LIST_MIN_BUCKET_SIZE (1 << SGEN_ARRAY_LIST_MIN_BUCKET_BITS)
+
+typedef void (*SgenArrayListBucketAllocCallback) (gpointer *bucket, guint32 new_bucket_size, gboolean alloc);
+typedef gboolean (*SgenArrayListIsSlotSetFunc) (volatile gpointer *slot);
+typedef gboolean (*SgenArrayListSetSlotFunc) (volatile gpointer *slot, gpointer ptr, int data);
+
+/*
+ * 'entries' is an array of pointers to buckets of increasing size. The first
+ * bucket has size 'MIN_BUCKET_SIZE', and each bucket is twice the size of the
+ * previous, i.e.:
+ *
+ *           |-------|-- MIN_BUCKET_SIZE
+ *    [0] -> xxxxxxxx
+ *    [1] -> xxxxxxxxxxxxxxxx
+ *    [2] -> xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
+ *    ...
+ *
+ * 'slot_hint' denotes the position of the last allocation, so that the
+ * whole array needn't be searched on every allocation.
+ *
+ * The size of the spine, 'SGEN_ARRAY_LIST_BUCKETS', is chosen so
+ * that the maximum number of entries is no less than G_MAXUINT32.
+ */
+
+typedef struct {
+       volatile gpointer *volatile entries [SGEN_ARRAY_LIST_BUCKETS];
+       volatile guint32 capacity;
+       volatile guint32 slot_hint;
+       volatile guint32 next_slot;
+       SgenArrayListBucketAllocCallback bucket_alloc_callback;
+       SgenArrayListIsSlotSetFunc is_slot_set_func;
+       SgenArrayListSetSlotFunc set_slot_func;
+       int mem_type; /* sgen internal mem type or -1 for malloc allocation */
+} SgenArrayList;
+
+/*
+ * Computes floor(log2(index + MIN_BUCKET_SIZE)) - 1, giving the index
+ * of the bucket containing a slot.
+ */
+static inline guint32
+sgen_array_list_index_bucket (guint32 index)
+{
+#ifdef __GNUC__
+       return CHAR_BIT * sizeof (index) - __builtin_clz (index + SGEN_ARRAY_LIST_MIN_BUCKET_SIZE) - 1 - SGEN_ARRAY_LIST_MIN_BUCKET_BITS;
+#else
+       guint count = 0;
+       index += SGEN_ARRAY_LIST_MIN_BUCKET_SIZE;
+       while (index) {
+               ++count;
+               index >>= 1;
+       }
+       return count - 1 - SGEN_ARRAY_LIST_MIN_BUCKET_BITS;
+#endif
+}
+
+static inline guint32
+sgen_array_list_bucket_size (guint32 index)
+{
+       return 1 << (index + SGEN_ARRAY_LIST_MIN_BUCKET_BITS);
+}
+
+static inline void
+sgen_array_list_bucketize (guint32 index, guint32 *bucket, guint32 *offset)
+{
+       *bucket = sgen_array_list_index_bucket (index);
+       *offset = index - sgen_array_list_bucket_size (*bucket) + SGEN_ARRAY_LIST_MIN_BUCKET_SIZE;
+}
+
+static inline volatile gpointer *
+sgen_array_list_get_slot (SgenArrayList *array, guint32 index)
+{
+       guint32 bucket, offset;
+
+       SGEN_ASSERT (0, index < array->capacity, "Why are we accessing an entry that is not allocated");
+
+       sgen_array_list_bucketize (index, &bucket, &offset);
+       return &(array->entries [bucket] [offset]);
+}
+
+#define SGEN_ARRAY_LIST_INIT(bucket_alloc_callback, is_slot_set_func, set_slot_func, mem_type) { { NULL }, 0, 0, 0, (bucket_alloc_callback), (is_slot_set_func), (set_slot_func), (mem_type) }
+
+#define SGEN_ARRAY_LIST_FOREACH_SLOT(array, slot) {                    \
+       guint32 __bucket, __offset;                                     \
+       const guint32 __max_bucket = sgen_array_list_index_bucket ((array)->capacity); \
+       guint32 __index = 0;                                            \
+       const guint32 __next_slot = (array)->next_slot;                 \
+       for (__bucket = 0; __bucket < __max_bucket; ++__bucket) {       \
+               volatile gpointer *__entries = (array)->entries [__bucket]; \
+               for (__offset = 0; __offset < sgen_array_list_bucket_size (__bucket); ++__offset, ++__index) { \
+                       if (__index >= __next_slot)                     \
+                               break;                                  \
+                       slot = &__entries [__offset];
+
+#define SGEN_ARRAY_LIST_END_FOREACH_SLOT       } } }
+
+#define SGEN_ARRAY_LIST_FOREACH_SLOT_RANGE(array, begin, end, slot, index) {   \
+       for (index = (begin); index < (end); index++) {         \
+               guint32 __bucket, __offset;                             \
+               volatile gpointer *__entries;                           \
+               sgen_array_list_bucketize (index, &__bucket, &__offset); \
+               __entries = (array)->entries [__bucket];                \
+               slot = &__entries [__offset];
+
+#define SGEN_ARRAY_LIST_END_FOREACH_SLOT_RANGE } }
+
+guint32 sgen_array_list_add (SgenArrayList *array, gpointer ptr, int data, gboolean increase_size_before_set);
+guint32 sgen_array_list_find (SgenArrayList *array, gpointer ptr);
+void sgen_array_list_remove_nulls (SgenArrayList *array);
+
+#endif
index f88b933a68e49f9d3e9fc3f81cda93d1f9e2d51a..05dfe7d90743b041f12bcf26d587213920fe46c0 100644 (file)
@@ -9,18 +9,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -342,6 +331,29 @@ sgen_card_table_update_mod_union (guint8 *dest, char *obj, mword obj_size, size_
                *out_num_cards = num_cards;
 }
 
+/* Preclean cards and saves the cards that need to be scanned afterwards in cards_preclean */
+void
+sgen_card_table_preclean_mod_union (guint8 *cards, guint8 *cards_preclean, size_t num_cards)
+{
+       size_t i;
+
+       memcpy (cards_preclean, cards, num_cards);
+       for (i = 0; i < num_cards; i++) {
+               if (cards_preclean [i]) {
+                       cards [i] = 0;
+               }
+       }
+       /*
+        * When precleaning we need to make sure the card cleaning
+        * takes place before the object is scanned. If we don't
+        * do this we could finish scanning the object and, before
+        * the cleaning of the card takes place, another thread
+        * could dirty the object, mark the mod_union card only for
+        * us to clean it back, without scanning the object again.
+        */
+       mono_memory_barrier ();
+}
+
 #ifdef SGEN_HAVE_OVERLAPPING_CARDS
 
 static void
@@ -426,11 +438,11 @@ sgen_card_table_scan_remsets (ScanCopyContext ctx)
        sgen_card_table_clear_cards ();
 #endif
        SGEN_TV_GETTIME (atv);
-       sgen_get_major_collector ()->scan_card_table (FALSE, ctx);
+       sgen_get_major_collector ()->scan_card_table (CARDTABLE_SCAN_GLOBAL, ctx);
        SGEN_TV_GETTIME (btv);
        last_major_scan_time = SGEN_TV_ELAPSED (atv, btv); 
        major_card_scan_time += last_major_scan_time;
-       sgen_los_scan_card_table (FALSE, ctx);
+       sgen_los_scan_card_table (CARDTABLE_SCAN_GLOBAL, ctx);
        SGEN_TV_GETTIME (atv);
        last_los_scan_time = SGEN_TV_ELAPSED (btv, atv);
        los_card_scan_time += last_los_scan_time;
@@ -477,11 +489,11 @@ sgen_card_table_dump_obj_card (GCObject *object, size_t size, void *dummy)
 #endif
 
 void
-sgen_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, gboolean mod_union, ScanCopyContext ctx)
+sgen_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, ScanCopyContext ctx)
 {
        HEAVY_STAT (++large_objects);
 
-       if (sgen_client_cardtable_scan_object (obj, block_obj_size, cards, mod_union, ctx))
+       if (sgen_client_cardtable_scan_object (obj, block_obj_size, cards, ctx))
                return;
 
        HEAVY_STAT (++bloby_objects);
index bda77e4e925fd5149ee09a244322af12c2c9bbaa..059fb77fa64925d61f73ff1311c1f7b979b7343e 100644 (file)
@@ -2,24 +2,7 @@
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_CARD_TABLE_INLINES_H__
 #define __MONO_SGEN_CARD_TABLE_INLINES_H__
@@ -31,7 +14,7 @@ void sgen_card_table_reset_region (mword start, mword end);
 void* sgen_card_table_align_pointer (void *ptr);
 void sgen_card_table_mark_range (mword address, mword size);
 void sgen_cardtable_scan_object (GCObject *obj, mword obj_size, guint8 *cards,
-               gboolean mod_union, ScanCopyContext ctx);
+               ScanCopyContext ctx);
 
 gboolean sgen_card_table_get_card_data (guint8 *dest, mword address, mword cards);
 
@@ -40,6 +23,7 @@ void sgen_card_table_free_mod_union (guint8 *mod_union, char *obj, mword obj_siz
 
 void sgen_card_table_update_mod_union_from_cards (guint8 *dest, guint8 *start_card, size_t num_cards);
 void sgen_card_table_update_mod_union (guint8 *dest, char *obj, mword obj_size, size_t *out_num_cards);
+void sgen_card_table_preclean_mod_union (guint8 *cards, guint8 *cards_preclean, size_t num_cards);
 
 guint8* sgen_get_card_table_configuration (int *shift_bits, gpointer *mask);
 
index edf9dde8439e1f1cd4bef151e6dde539d853caf3..4cf9f003d5584bb55b5c7ab30f9170661647c3f7 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/sgen/sgen-pointer-queue.h"
@@ -105,7 +94,7 @@ void sgen_client_ensure_weak_gchandles_accessible (void);
  * parts of the object based on which cards are marked, do so and return TRUE.  Otherwise,
  * return FALSE.
  */
-gboolean sgen_client_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, gboolean mod_union, ScanCopyContext ctx);
+gboolean sgen_client_cardtable_scan_object (GCObject *obj, mword block_obj_size, guint8 *cards, ScanCopyContext ctx);
 
 /*
  * Called after nursery objects have been pinned.  No action is necessary.
index 11a8998478e765e8083e337c57a9f48c6fb7a9ee..429dcb26af30a8b2370225bf988dc247aa7db7b5 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGENCONF_H__
 #define __MONO_SGENCONF_H__
index 2b7bc60670a3751b20566b5c35f100d1b0d8ecf8..016fc462e0e762772ccbb9f6701eaf4c583937af 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 extern guint64 stat_copy_object_called_nursery;
index 27e8cb0addf54d760ef99b1b351bd011eab5eb73..28e77a77e87d53c9a3145a586f0545f3b049c639 100644 (file)
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 1d5b36637eede053a25c3593da22d285e8a0c866..6ddea6d621301348aa2035c5f227994d8f695631 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 #ifdef HAVE_SGEN_GC
@@ -197,7 +186,7 @@ mono_gc_make_descr_for_array (int vector, gsize *elem_bitmap, int numbits, size_
                }
                /* Note: we also handle structs with just ref fields */
                if (num_set * sizeof (gpointer) == elem_size) {
-                       return desc | VECTOR_SUBTYPE_REFS | ((gssize)(-1) << 16);
+                       return desc | VECTOR_SUBTYPE_REFS | ((gsize)(-1) << 16);
                }
                /* FIXME: try run-len first */
                /* Note: we can't skip the object header here, because it's not present */
index c61fa5f74d6bda3391e959ce4b0b580a15d0cdf2..2b1f9e4da49c2bf558145f09e1757c354f4b1d06 100644 (file)
@@ -7,18 +7,7 @@
  *
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_DESCRIPTOR_H__
 #define __MONO_SGEN_DESCRIPTOR_H__
index 5130b1c6b3894de6727e094a73032dd045a6f42c..dd7cca93dbecc2634a3c6dce3ece2278a5d040ca 100644 (file)
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 89af85f4387d92646edc38554aa138dd0b9dbdec..5ec907371f38451a493b5de735ff26c44620c6cf 100644 (file)
  * Copyright 2011 Xamarin, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  *
  * Important: allocation provides always zeroed memory, having to do
  * a memset after allocation is deadly for performance.
@@ -245,6 +234,8 @@ static gboolean do_verify_nursery = FALSE;
 static gboolean do_dump_nursery_content = FALSE;
 static gboolean enable_nursery_canaries = FALSE;
 
+static gboolean precleaning_enabled = TRUE;
+
 #ifdef HEAVY_STATISTICS
 guint64 stat_objects_alloced_degraded = 0;
 guint64 stat_bytes_alloced_degraded = 0;
@@ -341,7 +332,6 @@ nursery_canaries_enabled (void)
  * ######################################################################
  */
 MonoCoopMutex gc_mutex;
-gboolean sgen_try_free_some_memory;
 
 #define SCAN_START_SIZE        SGEN_SCAN_START_SIZE
 
@@ -706,6 +696,8 @@ pin_objects_from_nursery_pin_queue (gboolean do_scan_objects, ScanCopyContext ct
                        definitely_pinned [count] = obj_to_pin;
                        count++;
                }
+               if (concurrent_collection_in_progress)
+                       sgen_pinning_register_pinned_in_nursery (obj_to_pin);
 
        next_pin_queue_entry:
                last = addr;
@@ -1084,6 +1076,12 @@ finish_gray_stack (int generation, ScanCopyContext ctx)
        if (sgen_client_bridge_need_processing ())
                sgen_client_bridge_reset_data ();
 
+       /*
+        * Mark all strong toggleref objects. This must be done before we walk ephemerons or finalizers
+        * to ensure they see the full set of live objects.
+        */
+       sgen_client_mark_togglerefs (start_addr, end_addr, ctx);
+
        /*
         * Walk the ephemeron tables marking all values with reachable keys. This must be completely done
         * before processing finalizable objects and non-tracking weak links to avoid finalizing/clearing
@@ -1096,8 +1094,6 @@ finish_gray_stack (int generation, ScanCopyContext ctx)
                ++ephemeron_rounds;
        } while (!done_with_ephemerons);
 
-       sgen_client_mark_togglerefs (start_addr, end_addr, ctx);
-
        if (sgen_client_bridge_need_processing ()) {
                /*Make sure the gray stack is empty before we process bridge objects so we get liveness right*/
                sgen_drain_gray_stack (ctx);
@@ -1167,7 +1163,7 @@ finish_gray_stack (int generation, ScanCopyContext ctx)
        sgen_client_clear_togglerefs (start_addr, end_addr, ctx);
 
        TV_GETTIME (btv);
-       SGEN_LOG (2, "Finalize queue handling scan for %s generation: %ld usecs %d ephemeron rounds", generation_name (generation), TV_ELAPSED (atv, btv), ephemeron_rounds);
+       SGEN_LOG (2, "Finalize queue handling scan for %s generation: %lld usecs %d ephemeron rounds", generation_name (generation), TV_ELAPSED (atv, btv), ephemeron_rounds);
 
        /*
         * handle disappearing links
@@ -1392,7 +1388,7 @@ job_scan_major_mod_union_card_table (void *worker_data_untyped, SgenThreadPoolJo
        ScanCopyContext ctx = CONTEXT_FROM_OBJECT_OPERATIONS (job_data->ops, sgen_workers_get_job_gray_queue (worker_data));
 
        g_assert (concurrent_collection_in_progress);
-       major_collector.scan_card_table (TRUE, ctx);
+       major_collector.scan_card_table (CARDTABLE_SCAN_MOD_UNION, ctx);
 }
 
 static void
@@ -1403,7 +1399,22 @@ job_scan_los_mod_union_card_table (void *worker_data_untyped, SgenThreadPoolJob
        ScanCopyContext ctx = CONTEXT_FROM_OBJECT_OPERATIONS (job_data->ops, sgen_workers_get_job_gray_queue (worker_data));
 
        g_assert (concurrent_collection_in_progress);
-       sgen_los_scan_card_table (TRUE, ctx);
+       sgen_los_scan_card_table (CARDTABLE_SCAN_MOD_UNION, ctx);
+}
+
+static void
+job_mod_union_preclean (void *worker_data_untyped, SgenThreadPoolJob *job)
+{
+       WorkerData *worker_data = (WorkerData *)worker_data_untyped;
+       ScanJob *job_data = (ScanJob*)job;
+       ScanCopyContext ctx = CONTEXT_FROM_OBJECT_OPERATIONS (job_data->ops, sgen_workers_get_job_gray_queue (worker_data));
+
+       g_assert (concurrent_collection_in_progress);
+
+       major_collector.scan_card_table (CARDTABLE_SCAN_MOD_UNION_PRECLEAN, ctx);
+       sgen_los_scan_card_table (CARDTABLE_SCAN_MOD_UNION_PRECLEAN, ctx);
+
+       sgen_scan_pin_queue_objects (ctx);
 }
 
 static void
@@ -1546,7 +1557,7 @@ collect_nursery (SgenGrayQueue *unpin_queue, gboolean finish_up_concurrent_mark)
 
        TV_GETTIME (atv);
        time_minor_pinning += TV_ELAPSED (btv, atv);
-       SGEN_LOG (2, "Finding pinned pointers: %zd in %ld usecs", sgen_get_pinned_count (), TV_ELAPSED (btv, atv));
+       SGEN_LOG (2, "Finding pinned pointers: %zd in %lld usecs", sgen_get_pinned_count (), TV_ELAPSED (btv, atv));
        SGEN_LOG (4, "Start scan with %zd pinned objects", sgen_get_pinned_count ());
 
        sj = (ScanJob*)sgen_thread_pool_job_alloc ("scan remset", job_remembered_set_scan, sizeof (ScanJob));
@@ -1556,7 +1567,7 @@ collect_nursery (SgenGrayQueue *unpin_queue, gboolean finish_up_concurrent_mark)
        /* we don't have complete write barrier yet, so we scan all the old generation sections */
        TV_GETTIME (btv);
        time_minor_scan_remsets += TV_ELAPSED (atv, btv);
-       SGEN_LOG (2, "Old generation scan: %ld usecs", TV_ELAPSED (atv, btv));
+       SGEN_LOG (2, "Old generation scan: %lld usecs", TV_ELAPSED (atv, btv));
 
        sgen_pin_stats_print_class_stats ();
 
@@ -1597,7 +1608,7 @@ collect_nursery (SgenGrayQueue *unpin_queue, gboolean finish_up_concurrent_mark)
        sgen_client_binary_protocol_reclaim_end (GENERATION_NURSERY);
        TV_GETTIME (btv);
        time_minor_fragment_creation += TV_ELAPSED (atv, btv);
-       SGEN_LOG (2, "Fragment creation: %ld usecs, %lu bytes available", TV_ELAPSED (atv, btv), (unsigned long)fragment_total);
+       SGEN_LOG (2, "Fragment creation: %lld usecs, %lu bytes available", TV_ELAPSED (atv, btv), (unsigned long)fragment_total);
 
        if (consistency_check_at_minor_collection)
                sgen_check_major_refs ();
@@ -1698,7 +1709,7 @@ major_copy_or_mark_from_roots (size_t *old_next_pin_slot, CopyOrMarkFromRootsMod
 
        sgen_client_pre_collection_checks ();
 
-       if (!concurrent) {
+       if (mode != COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT) {
                /* Remsets are not useful for a major collection */
                remset.clear_cards ();
        }
@@ -1709,8 +1720,20 @@ major_copy_or_mark_from_roots (size_t *old_next_pin_slot, CopyOrMarkFromRootsMod
        sgen_init_pinning ();
        SGEN_LOG (6, "Collecting pinned addresses");
        pin_from_roots ((void*)lowest_heap_address, (void*)highest_heap_address, ctx);
-
+       if (mode == COPY_OR_MARK_FROM_ROOTS_FINISH_CONCURRENT) {
+               /* Pin cemented objects that were forced */
+               sgen_pin_cemented_objects ();
+       }
        sgen_optimize_pin_queue ();
+       if (mode == COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT) {
+               /*
+                * Cemented objects that are in the pinned list will be marked. When
+                * marking concurrently we won't mark mod-union cards for these objects.
+                * Instead they will remain cemented until the next major collection,
+                * when we will recheck if they are still pinned in the roots.
+                */
+               sgen_cement_force_pinned ();
+       }
 
        sgen_client_collecting_major_1 ();
 
@@ -1762,24 +1785,19 @@ major_copy_or_mark_from_roots (size_t *old_next_pin_slot, CopyOrMarkFromRootsMod
 
        TV_GETTIME (btv);
        time_major_pinning += TV_ELAPSED (atv, btv);
-       SGEN_LOG (2, "Finding pinned pointers: %zd in %ld usecs", sgen_get_pinned_count (), TV_ELAPSED (atv, btv));
+       SGEN_LOG (2, "Finding pinned pointers: %zd in %lld usecs", sgen_get_pinned_count (), TV_ELAPSED (atv, btv));
        SGEN_LOG (4, "Start scan with %zd pinned objects", sgen_get_pinned_count ());
 
        major_collector.init_to_space ();
 
-       /*
-        * The concurrent collector doesn't move objects, neither on
-        * the major heap nor in the nursery, so we can mark even
-        * before pinning has finished.  For the non-concurrent
-        * collector we start the workers after pinning.
-        */
-       if (mode == COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT) {
-               SGEN_ASSERT (0, sgen_workers_all_done (), "Why are the workers not done when we start or finish a major collection?");
-               sgen_workers_start_all_workers (object_ops);
-               gray_queue_enable_redirect (WORKERS_DISTRIBUTE_GRAY_QUEUE);
-       } else if (mode == COPY_OR_MARK_FROM_ROOTS_FINISH_CONCURRENT) {
+       SGEN_ASSERT (0, sgen_workers_all_done (), "Why are the workers not done when we start or finish a major collection?");
+       if (mode == COPY_OR_MARK_FROM_ROOTS_FINISH_CONCURRENT) {
                if (sgen_workers_have_idle_work ()) {
-                       sgen_workers_start_all_workers (object_ops);
+                       /*
+                        * We force the finish of the worker with the new object ops context
+                        * which can also do copying. We need to have finished pinning.
+                        */
+                       sgen_workers_start_all_workers (object_ops, NULL);
                        sgen_workers_join ();
                }
        }
@@ -1795,15 +1813,29 @@ major_copy_or_mark_from_roots (size_t *old_next_pin_slot, CopyOrMarkFromRootsMod
 
        sgen_client_collecting_major_3 (&fin_ready_queue, &critical_fin_queue);
 
-       /*
-        * FIXME: is this the right context?  It doesn't seem to contain a copy function
-        * unless we're concurrent.
-        */
-       enqueue_scan_from_roots_jobs (heap_start, heap_end, object_ops, mode == COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT);
+       enqueue_scan_from_roots_jobs (heap_start, heap_end, object_ops, FALSE);
 
        TV_GETTIME (btv);
        time_major_scan_roots += TV_ELAPSED (atv, btv);
 
+       /*
+        * We start the concurrent worker after pinning and after we scanned the roots
+        * in order to make sure that the worker does not finish before handling all
+        * the roots.
+        */
+       if (mode == COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT) {
+               if (precleaning_enabled) {
+                       ScanJob *sj;
+                       /* Mod union preclean job */
+                       sj = (ScanJob*)sgen_thread_pool_job_alloc ("preclean mod union cardtable", job_mod_union_preclean, sizeof (ScanJob));
+                       sj->ops = object_ops;
+                       sgen_workers_start_all_workers (object_ops, &sj->job);
+               } else {
+                       sgen_workers_start_all_workers (object_ops, NULL);
+               }
+               gray_queue_enable_redirect (WORKERS_DISTRIBUTE_GRAY_QUEUE);
+       }
+
        if (mode == COPY_OR_MARK_FROM_ROOTS_FINISH_CONCURRENT) {
                ScanJob *sj;
 
@@ -1827,11 +1859,6 @@ static void
 major_finish_copy_or_mark (CopyOrMarkFromRootsMode mode)
 {
        if (mode == COPY_OR_MARK_FROM_ROOTS_START_CONCURRENT) {
-               /*
-                * Prepare the pin queue for the next collection.  Since pinning runs on the worker
-                * threads we must wait for the jobs to finish before we can reset it.
-                */
-               sgen_workers_wait_for_jobs_finished ();
                sgen_finish_pinning ();
 
                sgen_pin_stats_reset ();
@@ -2931,6 +2958,15 @@ sgen_gc_init (void)
                                continue;
                        }
 
+                       if (!strcmp (opt, "precleaning")) {
+                               precleaning_enabled = TRUE;
+                               continue;
+                       }
+                       if (!strcmp (opt, "no-precleaning")) {
+                               precleaning_enabled = FALSE;
+                               continue;
+                       }
+
                        if (major_collector.handle_gc_param && major_collector.handle_gc_param (opt))
                                continue;
 
@@ -2976,6 +3012,7 @@ sgen_gc_init (void)
 
        alloc_nursery ();
 
+       sgen_pinning_init ();
        sgen_cement_init (cement_enabled);
 
        if ((env = g_getenv (MONO_GC_DEBUG_NAME))) {
@@ -3147,11 +3184,7 @@ sgen_gc_lock (void)
 void
 sgen_gc_unlock (void)
 {
-       gboolean try_free = sgen_try_free_some_memory;
-       sgen_try_free_some_memory = FALSE;
        mono_coop_mutex_unlock (&gc_mutex);
-       if (try_free)
-               mono_thread_hazardous_try_free_some ();
 }
 
 void
@@ -3218,8 +3251,6 @@ sgen_restart_world (int generation, GGTimingInfo *timing)
 
        binary_protocol_world_restarted (generation, sgen_timestamp ());
 
-       sgen_try_free_some_memory = TRUE;
-
        if (sgen_client_bridge_need_processing ())
                sgen_client_bridge_processing_finish (generation);
 
index 4b2f895d890badc5f42157ebe4009f57211ad1b4..f3d868a541648015aba3ef73d8a88f8345a30390 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGENGC_H__
 #define __MONO_SGENGC_H__
@@ -407,12 +396,14 @@ gboolean sgen_is_worker_thread (MonoNativeThreadId thread);
 typedef void (*CopyOrMarkObjectFunc) (GCObject**, SgenGrayQueue*);
 typedef void (*ScanObjectFunc) (GCObject *obj, SgenDescriptor desc, SgenGrayQueue*);
 typedef void (*ScanVTypeFunc) (GCObject *full_object, char *start, SgenDescriptor desc, SgenGrayQueue* BINARY_PROTOCOL_ARG (size_t size));
+typedef void (*ScanPtrFieldFunc) (GCObject *obj, GCObject **ptr, SgenGrayQueue* queue);
 typedef gboolean (*DrainGrayStackFunc) (SgenGrayQueue *queue);
 
 typedef struct {
        CopyOrMarkObjectFunc copy_or_mark_object;
        ScanObjectFunc scan_object;
        ScanVTypeFunc scan_vtype;
+       ScanPtrFieldFunc scan_ptr_field;
        /* Drain stack optimized for the above functions */
        DrainGrayStackFunc drain_gray_stack;
        /*FIXME add allocation function? */
@@ -595,6 +586,12 @@ typedef struct
        size_t num_unique_scanned_objects;
 } ScannedObjectCounts;
 
+typedef enum {
+       CARDTABLE_SCAN_GLOBAL = 0,
+       CARDTABLE_SCAN_MOD_UNION = 1,
+       CARDTABLE_SCAN_MOD_UNION_PRECLEAN = CARDTABLE_SCAN_MOD_UNION | 2,
+} CardTableScanType;
+
 typedef struct _SgenMajorCollector SgenMajorCollector;
 struct _SgenMajorCollector {
        size_t section_size;
@@ -624,7 +621,7 @@ struct _SgenMajorCollector {
        void (*free_non_pinned_object) (GCObject *obj, size_t size);
        void (*pin_objects) (SgenGrayQueue *queue);
        void (*pin_major_object) (GCObject *obj, SgenGrayQueue *queue);
-       void (*scan_card_table) (gboolean mod_union, ScanCopyContext ctx);
+       void (*scan_card_table) (CardTableScanType scan_type, ScanCopyContext ctx);
        void (*iterate_live_block_ranges) (sgen_cardtable_block_callback callback);
        void (*update_cardtable_mod_union) (void);
        void (*init_to_space) (void);
@@ -850,7 +847,7 @@ void sgen_los_sweep (void);
 gboolean sgen_ptr_is_in_los (char *ptr, char **start);
 void sgen_los_iterate_objects (IterateObjectCallbackFunc cb, void *user_data);
 void sgen_los_iterate_live_block_ranges (sgen_cardtable_block_callback callback);
-void sgen_los_scan_card_table (gboolean mod_union, ScanCopyContext ctx);
+void sgen_los_scan_card_table (CardTableScanType scan_type, ScanCopyContext ctx);
 void sgen_los_update_cardtable_mod_union (void);
 void sgen_los_count_cards (long long *num_total_cards, long long *num_marked_cards);
 gboolean sgen_los_is_valid_object (char *object);
index 9d00c397b9d6fb996f780a454aa56eb8647c65c2..6fc24a2151a8e4b464f94cb5724afe32af392a6e 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -22,6 +11,7 @@
 
 #include "mono/sgen/sgen-gc.h"
 #include "mono/sgen/sgen-client.h"
+#include "mono/sgen/sgen-array-list.h"
 #include "mono/utils/mono-membar.h"
 
 #ifdef HEAVY_STATISTICS
@@ -29,26 +19,9 @@ static volatile guint32 stat_gc_handles_allocated = 0;
 static volatile guint32 stat_gc_handles_max_allocated = 0;
 #endif
 
-#define BUCKETS (32 - MONO_GC_HANDLE_TYPE_SHIFT)
-#define MIN_BUCKET_BITS (5)
-#define MIN_BUCKET_SIZE (1 << MIN_BUCKET_BITS)
-
 /*
  * A table of GC handle data, implementing a simple lock-free bitmap allocator.
  *
- * 'entries' is an array of pointers to buckets of increasing size. The first
- * bucket has size 'MIN_BUCKET_SIZE', and each bucket is twice the size of the
- * previous, i.e.:
- *
- *           |-------|-- MIN_BUCKET_SIZE
- *    [0] -> xxxxxxxx
- *    [1] -> xxxxxxxxxxxxxxxx
- *    [2] -> xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
- *    ...
- *
- * The size of the spine, 'BUCKETS', is chosen so that the maximum number of
- * entries is no less than the maximum index value of a GC handle.
- *
  * Each entry in a bucket is a pointer with two tag bits: if
  * 'GC_HANDLE_OCCUPIED' returns true for a slot, then the slot is occupied; if
  * so, then 'GC_HANDLE_VALID' gives whether the entry refers to a valid (1) or
@@ -56,51 +29,13 @@ static volatile guint32 stat_gc_handles_max_allocated = 0;
  * object pointer. If the reference is NULL, and 'GC_HANDLE_TYPE_IS_WEAK' is
  * true for 'type', then the pointer is a metadata pointer--this allows us to
  * retrieve the domain ID of an expired weak reference in Mono.
- *
- * Finally, 'slot_hint' denotes the position of the last allocation, so that the
- * whole array needn't be searched on every allocation.
  */
 
 typedef struct {
-       volatile gpointer *volatile entries [BUCKETS];
-       volatile guint32 capacity;
-       volatile guint32 slot_hint;
-       volatile guint32 max_index;
+       SgenArrayList entries_array;
        guint8 type;
 } HandleData;
 
-static inline guint
-bucket_size (guint index)
-{
-       return 1 << (index + MIN_BUCKET_BITS);
-}
-
-/* Computes floor(log2(index + MIN_BUCKET_SIZE)) - 1, giving the index
- * of the bucket containing a slot.
- */
-static inline guint
-index_bucket (guint index)
-{
-#ifdef __GNUC__
-       return CHAR_BIT * sizeof (index) - __builtin_clz (index + MIN_BUCKET_SIZE) - 1 - MIN_BUCKET_BITS;
-#else
-       guint count = 0;
-       index += MIN_BUCKET_SIZE;
-       while (index) {
-               ++count;
-               index >>= 1;
-       }
-       return count - 1 - MIN_BUCKET_BITS;
-#endif
-}
-
-static inline void
-bucketize (guint index, guint *bucket, guint *offset)
-{
-       *bucket = index_bucket (index);
-       *offset = index - bucket_size (*bucket) + MIN_BUCKET_SIZE;
-}
-
 static void
 protocol_gchandle_update (int handle_type, gpointer link, gpointer old_value, gpointer new_value)
 {
@@ -136,21 +71,38 @@ try_set_slot (volatile gpointer *slot, GCObject *obj, gpointer old, GCHandleType
        return NULL;
 }
 
+static inline gboolean
+is_slot_set (volatile gpointer *slot)
+{
+       gpointer entry = *slot;
+       if (MONO_GC_HANDLE_OCCUPIED (entry))
+               return TRUE;
+       return FALSE;
+}
+
 /* Try to claim a slot by setting its occupied bit. */
 static inline gboolean
-try_occupy_slot (HandleData *handles, guint bucket, guint offset, GCObject *obj, gboolean track)
+try_occupy_slot (volatile gpointer *slot, gpointer obj, int data)
 {
-       volatile gpointer *link_addr = &(handles->entries [bucket] [offset]);
-       if (MONO_GC_HANDLE_OCCUPIED (*link_addr))
+       if (is_slot_set (slot))
                return FALSE;
-       return try_set_slot (link_addr, obj, NULL, (GCHandleType)handles->type) != NULL;
+       return try_set_slot (slot, (GCObject *)obj, NULL, (GCHandleType)data) != NULL;
+}
+
+static void
+bucket_alloc_callback (gpointer *bucket, guint32 new_bucket_size, gboolean alloc)
+{
+       if (alloc)
+               sgen_register_root ((char *)bucket, new_bucket_size, SGEN_DESCRIPTOR_NULL, ROOT_TYPE_PINNED, MONO_ROOT_SOURCE_GC_HANDLE, "pinned gc handles");
+       else
+               sgen_deregister_root ((char *)bucket);
 }
 
 static HandleData gc_handles [] = {
-       { { NULL }, 0, 0, 0, (HANDLE_WEAK) },
-       { { NULL }, 0, 0, 0, (HANDLE_WEAK_TRACK) },
-       { { NULL }, 0, 0, 0, (HANDLE_NORMAL) },
-       { { NULL }, 0, 0, 0, (HANDLE_PINNED) }
+       { SGEN_ARRAY_LIST_INIT (NULL, is_slot_set, try_occupy_slot, -1), (HANDLE_WEAK) },
+       { SGEN_ARRAY_LIST_INIT (NULL, is_slot_set, try_occupy_slot, -1), (HANDLE_WEAK_TRACK) },
+       { SGEN_ARRAY_LIST_INIT (NULL, is_slot_set, try_occupy_slot, -1), (HANDLE_NORMAL) },
+       { SGEN_ARRAY_LIST_INIT (bucket_alloc_callback, is_slot_set, try_occupy_slot, -1), (HANDLE_PINNED) }
 };
 
 static HandleData *
@@ -164,102 +116,27 @@ void
 sgen_mark_normal_gc_handles (void *addr, SgenUserMarkFunc mark_func, void *gc_data)
 {
        HandleData *handles = gc_handles_for_type (HANDLE_NORMAL);
-       size_t bucket, offset;
-       const guint max_bucket = index_bucket (handles->capacity);
-       guint32 index = 0;
-       const guint32 max_index = handles->max_index;
-       for (bucket = 0; bucket < max_bucket; ++bucket) {
-               volatile gpointer *entries = handles->entries [bucket];
-               for (offset = 0; offset < bucket_size (bucket); ++offset, ++index) {
-                       volatile gpointer *entry;
-                       gpointer hidden, revealed;
-                       /* No need to iterate beyond the largest index ever allocated. */
-                       if (index > max_index)
-                               return;
-                       entry = &entries [offset];
-                       hidden = *entry;
-                       revealed = MONO_GC_REVEAL_POINTER (hidden, FALSE);
-                       if (!MONO_GC_HANDLE_IS_OBJECT_POINTER (hidden))
-                               continue;
-                       mark_func ((MonoObject **)&revealed, gc_data);
-                       g_assert (revealed);
-                       *entry = MONO_GC_HANDLE_OBJECT_POINTER (revealed, FALSE);
-               }
-       }
-}
-
-static guint
-handle_data_find_unset (HandleData *handles, guint32 begin, guint32 end)
-{
-       guint index;
-       gint delta = begin < end ? +1 : -1;
-       for (index = begin; index < end; index += delta) {
-               guint bucket, offset;
-               volatile gpointer *entries;
-               bucketize (index, &bucket, &offset);
-               entries = handles->entries [bucket];
-               g_assert (entries);
-               if (!MONO_GC_HANDLE_OCCUPIED (entries [offset]))
-                       return index;
-       }
-       return -1;
+       SgenArrayList *array = &handles->entries_array;
+       volatile gpointer *slot;
+       gpointer hidden, revealed;
+
+       SGEN_ARRAY_LIST_FOREACH_SLOT (array, slot) {
+               hidden = *slot;
+               revealed = MONO_GC_REVEAL_POINTER (hidden, FALSE);
+               if (!MONO_GC_HANDLE_IS_OBJECT_POINTER (hidden))
+                       continue;
+               mark_func ((MonoObject **)&revealed, gc_data);
+               g_assert (revealed);
+               *slot = MONO_GC_HANDLE_OBJECT_POINTER (revealed, FALSE);
+       } SGEN_ARRAY_LIST_END_FOREACH_SLOT;
 }
 
-/* Adds a bucket if necessary and possible. */
-static void
-handle_data_grow (HandleData *handles, guint32 old_capacity)
-{
-       const guint new_bucket = index_bucket (old_capacity);
-       const guint32 growth = bucket_size (new_bucket);
-       const guint32 new_capacity = old_capacity + growth;
-       gpointer *entries;
-       const size_t new_bucket_size = sizeof (**handles->entries) * growth;
-       if (handles->capacity >= new_capacity)
-               return;
-       entries = (gpointer *)g_malloc0 (new_bucket_size);
-       if (handles->type == HANDLE_PINNED)
-               sgen_register_root ((char *)entries, new_bucket_size, SGEN_DESCRIPTOR_NULL, ROOT_TYPE_PINNED, MONO_ROOT_SOURCE_GC_HANDLE, "pinned gc handles");
-       /* The zeroing of the newly allocated bucket must be complete before storing
-        * the new bucket pointer.
-        */
-       mono_memory_write_barrier ();
-       if (InterlockedCompareExchangePointer ((volatile gpointer *)&handles->entries [new_bucket], entries, NULL) == NULL) {
-               /* It must not be the case that we succeeded in setting the bucket
-                * pointer, while someone else succeeded in changing the capacity.
-                */
-               if (InterlockedCompareExchange ((volatile gint32 *)&handles->capacity, new_capacity, old_capacity) != old_capacity)
-                       g_assert_not_reached ();
-               handles->slot_hint = old_capacity;
-               return;
-       }
-       /* Someone beat us to the allocation. */
-       if (handles->type == HANDLE_PINNED)
-               sgen_deregister_root ((char *)entries);
-       g_free (entries);
-}
 
 static guint32
 alloc_handle (HandleData *handles, GCObject *obj, gboolean track)
 {
-       guint index;
-       guint32 res;
-       guint bucket, offset;
-       guint32 capacity;
-       guint32 slot_hint;
-       guint32 max_index;
-       if (!handles->capacity)
-               handle_data_grow (handles, 0);
-retry:
-       capacity = handles->capacity;
-       slot_hint = handles->slot_hint;
-       index = handle_data_find_unset (handles, slot_hint, capacity);
-       if (index == -1)
-               index = handle_data_find_unset (handles, 0, slot_hint);
-       if (index == -1) {
-               handle_data_grow (handles, capacity);
-               goto retry;
-       }
-       handles->slot_hint = index;
+       guint32 res, index;
+       SgenArrayList *array = &handles->entries_array;
 
        /*
         * If a GC happens shortly after a new bucket is allocated, the entire
@@ -267,21 +144,13 @@ retry:
         * we track the maximum index seen so far, so that we can skip the empty
         * slots.
         *
-        * Note that we update `max_index` before we even try occupying the
+        * Note that we update `next_slot` before we even try occupying the
         * slot.  If we did it the other way around and a GC happened in
         * between, the GC wouldn't know that the slot was occupied.  This is
         * not a huge deal since `obj` is on the stack and thus pinned anyway,
         * but hopefully some day it won't be anymore.
         */
-       do {
-               max_index = handles->max_index;
-               if (index <= max_index)
-                       break;
-       } while (InterlockedCompareExchange ((volatile gint32 *)&handles->max_index, index, max_index) != max_index);
-
-       bucketize (index, &bucket, &offset);
-       if (!try_occupy_slot (handles, bucket, offset, obj, track))
-               goto retry;
+       index = sgen_array_list_add (array, obj, handles->type, TRUE);
 #ifdef HEAVY_STATISTICS
        InterlockedIncrement ((volatile gint32 *)&stat_gc_handles_allocated);
        if (stat_gc_handles_allocated > stat_gc_handles_max_allocated)
@@ -308,38 +177,28 @@ void
 sgen_gchandle_iterate (GCHandleType handle_type, int max_generation, SgenGCHandleIterateCallback callback, gpointer user)
 {
        HandleData *handle_data = gc_handles_for_type (handle_type);
-       size_t bucket, offset;
-       guint max_bucket = index_bucket (handle_data->capacity);
-       guint32 index = 0;
-       guint32 max_index = handle_data->max_index;
+       SgenArrayList *array = &handle_data->entries_array;
+       gpointer hidden, result, occupied;
+       volatile gpointer *slot;
+
        /* If a new bucket has been allocated, but the capacity has not yet been
         * increased, nothing can yet have been allocated in the bucket because the
         * world is stopped, so we shouldn't miss any handles during iteration.
         */
-       for (bucket = 0; bucket < max_bucket; ++bucket) {
-               volatile gpointer *entries = handle_data->entries [bucket];
-               for (offset = 0; offset < bucket_size (bucket); ++offset, ++index) {
-                       gpointer hidden;
-                       gpointer result;
-                       /* Table must contain no garbage pointers. */
-                       gboolean occupied;
-                       /* No need to iterate beyond the largest index ever allocated. */
-                       if (index > max_index)
-                                       return;
-                       hidden = entries [offset];
-                       occupied = MONO_GC_HANDLE_OCCUPIED (hidden);
-                       g_assert (hidden ? occupied : !occupied);
-                       if (!occupied)
-                               continue;
-                       result = callback (hidden, handle_type, max_generation, user);
-                       if (result)
-                               SGEN_ASSERT (0, MONO_GC_HANDLE_OCCUPIED (result), "Why did the callback return an unoccupied entry?");
-                       else
-                               HEAVY_STAT (InterlockedDecrement ((volatile gint32 *)&stat_gc_handles_allocated));
-                       protocol_gchandle_update (handle_type, (gpointer)&entries [offset], hidden, result);
-                       entries [offset] = result;
-               }
-       }
+       SGEN_ARRAY_LIST_FOREACH_SLOT (array, slot) {
+               hidden = *slot;
+               occupied = (gpointer) MONO_GC_HANDLE_OCCUPIED (hidden);
+               g_assert (hidden ? !!occupied : !occupied);
+               if (!occupied)
+                       continue;
+               result = callback (hidden, handle_type, max_generation, user);
+               if (result)
+                       SGEN_ASSERT (0, MONO_GC_HANDLE_OCCUPIED (result), "Why did the callback return an unoccupied entry?");
+               else
+                       HEAVY_STAT (InterlockedDecrement ((volatile gint32 *)&stat_gc_handles_allocated));
+               protocol_gchandle_update (handle_type, (gpointer)slot, hidden, result);
+               *slot = result;
+       } SGEN_ARRAY_LIST_END_FOREACH_SLOT;
 }
 
 /**
@@ -453,43 +312,40 @@ mono_gchandle_get_target (guint32 gchandle)
        /* Invalid handles are possible; accessing one should produce NULL. (#34276) */
        if (!handles)
                return NULL;
-       guint bucket, offset;
-       g_assert (index < handles->capacity);
-       bucketize (index, &bucket, &offset);
-       return link_get (&handles->entries [bucket] [offset], MONO_GC_HANDLE_TYPE_IS_WEAK (type));
+       return link_get (sgen_array_list_get_slot (&handles->entries_array, index), MONO_GC_HANDLE_TYPE_IS_WEAK (type));
 }
 
 void
 sgen_gchandle_set_target (guint32 gchandle, GCObject *obj)
 {
-       guint index = MONO_GC_HANDLE_SLOT (gchandle);
+       guint32 index = MONO_GC_HANDLE_SLOT (gchandle);
        GCHandleType type = MONO_GC_HANDLE_TYPE (gchandle);
        HandleData *handles = gc_handles_for_type (type);
+       volatile gpointer *slot;
+       gpointer entry;
+
        if (!handles)
                return;
-       guint bucket, offset;
-       gpointer slot;
 
-       g_assert (index < handles->capacity);
-       bucketize (index, &bucket, &offset);
+       slot = sgen_array_list_get_slot (&handles->entries_array, index);
 
        do {
-               slot = handles->entries [bucket] [offset];
-               SGEN_ASSERT (0, MONO_GC_HANDLE_OCCUPIED (slot), "Why are we setting the target on an unoccupied slot?");
-       } while (!try_set_slot (&handles->entries [bucket] [offset], obj, slot, (GCHandleType)handles->type));
+               entry = *slot;
+               SGEN_ASSERT (0, MONO_GC_HANDLE_OCCUPIED (entry), "Why are we setting the target on an unoccupied slot?");
+       } while (!try_set_slot (slot, obj, entry, (GCHandleType)handles->type));
 }
 
 static gpointer
-mono_gchandle_slot_metadata (volatile gpointer *slot_addr, gboolean is_weak)
+mono_gchandle_slot_metadata (volatile gpointer *slot, gboolean is_weak)
 {
-       gpointer slot;
+       gpointer entry;
        gpointer metadata;
 retry:
-       slot = *slot_addr;
-       if (!MONO_GC_HANDLE_OCCUPIED (slot))
+       entry = *slot;
+       if (!MONO_GC_HANDLE_OCCUPIED (entry))
                return NULL;
-       if (MONO_GC_HANDLE_IS_OBJECT_POINTER (slot)) {
-               GCObject *obj = (GCObject *)MONO_GC_REVEAL_POINTER (slot, is_weak);
+       if (MONO_GC_HANDLE_IS_OBJECT_POINTER (entry)) {
+               GCObject *obj = (GCObject *)MONO_GC_REVEAL_POINTER (entry, is_weak);
                /* See note [dummy use]. */
                sgen_dummy_use (obj);
                /*
@@ -497,14 +353,14 @@ retry:
                 * at this point and recompute it later, in which case we would still use
                 * it.
                 */
-               if (*slot_addr != slot)
+               if (*slot != entry)
                        goto retry;
                return sgen_client_metadata_for_object (obj);
        }
-       metadata = MONO_GC_REVEAL_POINTER (slot, is_weak);
+       metadata = MONO_GC_REVEAL_POINTER (entry, is_weak);
        /* See note [dummy use]. */
        sgen_dummy_use (metadata);
-       if (*slot_addr != slot)
+       if (*slot != entry)
                goto retry;
        return metadata;
 }
@@ -512,16 +368,19 @@ retry:
 gpointer
 sgen_gchandle_get_metadata (guint32 gchandle)
 {
-       guint index = MONO_GC_HANDLE_SLOT (gchandle);
+       guint32 index = MONO_GC_HANDLE_SLOT (gchandle);
        GCHandleType type = MONO_GC_HANDLE_TYPE (gchandle);
        HandleData *handles = gc_handles_for_type (type);
+       volatile gpointer *slot;
+
        if (!handles)
                return NULL;
-       guint bucket, offset;
-       if (index >= handles->capacity)
+       if (index >= handles->entries_array.capacity)
                return NULL;
-       bucketize (index, &bucket, &offset);
-       return mono_gchandle_slot_metadata (&handles->entries [bucket] [offset], MONO_GC_HANDLE_TYPE_IS_WEAK (type));
+
+       slot = sgen_array_list_get_slot (&handles->entries_array, index);
+
+       return mono_gchandle_slot_metadata (slot, MONO_GC_HANDLE_TYPE_IS_WEAK (type));
 }
 
 /**
@@ -535,18 +394,20 @@ sgen_gchandle_get_metadata (guint32 gchandle)
 void
 mono_gchandle_free (guint32 gchandle)
 {
-       guint index = MONO_GC_HANDLE_SLOT (gchandle);
+       guint32 index = MONO_GC_HANDLE_SLOT (gchandle);
        GCHandleType type = MONO_GC_HANDLE_TYPE (gchandle);
        HandleData *handles = gc_handles_for_type (type);
+       volatile gpointer *slot;
+       gpointer entry;
        if (!handles)
                return;
-       guint bucket, offset;
-       gpointer slot;
-       bucketize (index, &bucket, &offset);
-       slot = handles->entries [bucket] [offset];
-       if (index < handles->capacity && MONO_GC_HANDLE_OCCUPIED (slot)) {
-               handles->entries [bucket] [offset] = NULL;
-               protocol_gchandle_update (handles->type, (gpointer)&handles->entries [bucket] [offset], slot, NULL);
+
+       slot = sgen_array_list_get_slot (&handles->entries_array, index);
+       entry = *slot;
+
+       if (index < handles->entries_array.capacity && MONO_GC_HANDLE_OCCUPIED (entry)) {
+               *slot = NULL;
+               protocol_gchandle_update (handles->type, (gpointer)slot, entry, NULL);
                HEAVY_STAT (InterlockedDecrement ((volatile gint32 *)&stat_gc_handles_allocated));
        } else {
                /* print a warning? */
@@ -616,7 +477,7 @@ null_link_if (gpointer hidden, GCHandleType handle_type, int max_generation, gpo
                return hidden;
 
        if (closure->predicate (obj, closure->data))
-               return NULL;
+               return MONO_GC_HANDLE_METADATA_POINTER (sgen_client_default_metadata (), GC_HANDLE_TYPE_IS_WEAK (handle_type));
 
        return hidden;
 }
index cb6694342fe484cc50bfdff9b940ca12ad0d6e92..809215136f9799d817b0b157d6c1ac972f085f93 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 #ifdef HAVE_SGEN_GC
index 79d2c701a0e4938ecd873144e72132546cbcae83..019f44c927c8e5fbee00e0d291c0234cb54b73cb 100644 (file)
@@ -4,18 +4,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_GRAY_H__
 #define __MONO_SGEN_GRAY_H__
index e5327399c584f0a83868b64313fb7679b7e2a26b..256e32b20a1b0108ae4c69d4328e7fe7fc0759ed 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 2f9ca117783ea2921c5379cd5dfeb202c6a3ea62..74c5c02a0278355074ab21273d63831791da11af 100644 (file)
@@ -1,24 +1,7 @@
 /*
  * Copyright Xamarin Inc (http://www.xamarin.com)
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 3853d3463480df2dd6497196c474f2b372e517b7..024e0192442b01e66e451189399ddf06bd99a18a 100644 (file)
@@ -1,24 +1,7 @@
 /*
  * Copyright Xamarin Inc (http://www.xamarin.com)
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_LAYOUT_STATS_H__
 #define __MONO_SGEN_LAYOUT_STATS_H__
index a89ec99fe353517580f0695f6d45e68859a18101..c22afd22f21d01c67998ee4e75dadedc444eb737 100644 (file)
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -73,6 +62,7 @@ struct _LOSSection {
        unsigned char *free_chunk_map;
 };
 
+/* We allow read only access on the list while sweep is not running */
 LOSObject *los_object_list = NULL;
 mword los_memory_usage = 0;
 
@@ -317,7 +307,8 @@ free_los_section_memory (LOSObject *obj, size_t size)
 void
 sgen_los_free_object (LOSObject *obj)
 {
-       SGEN_ASSERT (0, !obj->cardtable_mod_union, "We should never free a LOS object with a mod-union table.");
+       if (obj->cardtable_mod_union)
+               sgen_card_table_free_mod_union (obj->cardtable_mod_union, (char*)obj->data, sgen_los_object_size (obj));
 
 #ifndef LOS_DUMMY
        mword size = sgen_los_object_size (obj);
@@ -410,6 +401,11 @@ sgen_los_alloc_large_inner (GCVTable vtable, size_t size)
        *vtslot = vtable;
        sgen_update_heap_boundaries ((mword)obj->data, (mword)obj->data + size);
        obj->next = los_object_list;
+       /*
+        * We need a memory barrier so we don't expose as head of the los object list
+        * a LOSObject that doesn't have its fields initialized.
+        */
+       mono_memory_write_barrier ();
        los_object_list = obj;
        los_memory_usage += size;
        los_num_objects++;
@@ -438,12 +434,13 @@ sgen_los_sweep (void)
        for (bigobj = los_object_list; bigobj;) {
                SGEN_ASSERT (0, !SGEN_OBJECT_IS_PINNED (bigobj->data), "Who pinned a LOS object?");
 
-               if (bigobj->cardtable_mod_union) {
-                       sgen_card_table_free_mod_union (bigobj->cardtable_mod_union, (char*)bigobj->data, sgen_los_object_size (bigobj));
-                       bigobj->cardtable_mod_union = NULL;
-               }
-
                if (sgen_los_object_is_pinned (bigobj->data)) {
+                       if (bigobj->cardtable_mod_union) {
+                               mword obj_size = sgen_los_object_size (bigobj);
+                               mword num_cards = sgen_card_table_number_of_cards_in_range ((mword) bigobj->data, obj_size);
+                               memset (bigobj->cardtable_mod_union, 0, num_cards);
+                       }
+
                        sgen_los_unpin_object (bigobj->data);
                        sgen_update_heap_boundaries ((mword)bigobj->data, (mword)bigobj->data + sgen_los_object_size (bigobj));
                } else {
@@ -617,30 +614,44 @@ get_cardtable_mod_union_for_object (LOSObject *obj)
 }
 
 void
-sgen_los_scan_card_table (gboolean mod_union, ScanCopyContext ctx)
+sgen_los_scan_card_table (CardTableScanType scan_type, ScanCopyContext ctx)
 {
        LOSObject *obj;
 
-       binary_protocol_los_card_table_scan_start (sgen_timestamp (), mod_union);
+       binary_protocol_los_card_table_scan_start (sgen_timestamp (), scan_type & CARDTABLE_SCAN_MOD_UNION);
        for (obj = los_object_list; obj; obj = obj->next) {
+               mword num_cards = 0;
                guint8 *cards;
 
                if (!SGEN_OBJECT_HAS_REFERENCES (obj->data))
                        continue;
 
-               if (mod_union) {
+               if (scan_type & CARDTABLE_SCAN_MOD_UNION) {
                        if (!sgen_los_object_is_pinned (obj->data))
                                continue;
 
                        cards = get_cardtable_mod_union_for_object (obj);
                        g_assert (cards);
+                       if (scan_type == CARDTABLE_SCAN_MOD_UNION_PRECLEAN) {
+                               guint8 *cards_preclean;
+                               mword obj_size = sgen_los_object_size (obj);
+                               num_cards = sgen_card_table_number_of_cards_in_range ((mword) obj->data, obj_size);
+                               cards_preclean = (guint8 *)sgen_alloc_internal_dynamic (num_cards, INTERNAL_MEM_CARDTABLE_MOD_UNION, TRUE);
+
+                               sgen_card_table_preclean_mod_union (cards, cards_preclean, num_cards);
+
+                               cards = cards_preclean;
+                       }
                } else {
                        cards = NULL;
                }
 
-               sgen_cardtable_scan_object (obj->data, sgen_los_object_size (obj), cards, mod_union, ctx);
+               sgen_cardtable_scan_object (obj->data, sgen_los_object_size (obj), cards, ctx);
+
+               if (scan_type == CARDTABLE_SCAN_MOD_UNION_PRECLEAN)
+                       sgen_free_internal_dynamic (cards, num_cards, INTERNAL_MEM_CARDTABLE_MOD_UNION);
        }
-       binary_protocol_los_card_table_scan_end (sgen_timestamp (), mod_union);
+       binary_protocol_los_card_table_scan_end (sgen_timestamp (), scan_type & CARDTABLE_SCAN_MOD_UNION);
 }
 
 void
index a4b10ff85df2967fd4a4ba18740a88d838c6cd9b..826aca9dfd1fa7b5fb32ebe9d8f9f0a6175a036a 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #define collector_pin_object(obj, queue) do { \
index 677435a0a09cba9abd3d598b18ab7b20350451b1..ad2bb6fe272a44cbf08ce80ac65da5dbd177a0c7 100644 (file)
@@ -4,18 +4,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
@@ -234,7 +223,7 @@ SCAN_OBJECT_FUNCTION_NAME (GCObject *full_object, SgenDescriptor desc, SgenGrayQ
                                COPY_OR_MARK_FUNCTION_NAME ((ptr), __old, queue); \
                        }                                               \
                } else {                                                \
-                       if (G_UNLIKELY (sgen_ptr_in_nursery (__old) && !sgen_ptr_in_nursery ((ptr)))) \
+                       if (G_UNLIKELY (sgen_ptr_in_nursery (__old) && !sgen_ptr_in_nursery ((ptr)) && !sgen_cement_is_forced (__old))) \
                                mark_mod_union_card ((full_object), (void**)(ptr), __old); \
                        }                                               \
                } while (0)
@@ -246,7 +235,7 @@ SCAN_OBJECT_FUNCTION_NAME (GCObject *full_object, SgenDescriptor desc, SgenGrayQ
                        PREFETCH_READ (__old);                  \
                        COPY_OR_MARK_FUNCTION_NAME ((ptr), __old, queue); \
                } else {                                                \
-                       if (G_UNLIKELY (sgen_ptr_in_nursery (__old) && !sgen_ptr_in_nursery ((ptr)))) \
+                       if (G_UNLIKELY (sgen_ptr_in_nursery (__old) && !sgen_ptr_in_nursery ((ptr)) && !sgen_cement_is_forced (__old))) \
                                mark_mod_union_card ((full_object), (void**)(ptr), __old); \
                        }                                               \
                } while (0)
@@ -268,6 +257,37 @@ SCAN_OBJECT_FUNCTION_NAME (GCObject *full_object, SgenDescriptor desc, SgenGrayQ
 #include "sgen-scan-object.h"
 }
 
+#ifdef SCAN_VTYPE_FUNCTION_NAME 
+static void
+SCAN_VTYPE_FUNCTION_NAME (GCObject *full_object, char *start, SgenDescriptor desc, SgenGrayQueue *queue BINARY_PROTOCOL_ARG (size_t size))
+{
+       SGEN_OBJECT_LAYOUT_STATISTICS_DECLARE_BITMAP;
+
+#ifdef HEAVY_STATISTICS
+       /* FIXME: We're half scanning this object.  How do we account for that? */
+       //add_scanned_object (start);
+#endif
+
+       /* The descriptors include info about the object header as well */
+       start -= SGEN_CLIENT_OBJECT_HEADER_SIZE;
+
+       /* We use the same HANDLE_PTR from the obj scan function */
+#define SCAN_OBJECT_NOVTABLE
+#define SCAN_OBJECT_PROTOCOL
+#include "sgen-scan-object.h"
+
+       SGEN_OBJECT_LAYOUT_STATISTICS_COMMIT_BITMAP;
+}
+#endif
+
+#ifdef SCAN_PTR_FIELD_FUNCTION_NAME
+static void
+SCAN_PTR_FIELD_FUNCTION_NAME (GCObject *full_object, GCObject **ptr, SgenGrayQueue *queue)
+{
+       HANDLE_PTR (ptr, NULL);
+}
+#endif
+
 static gboolean
 DRAIN_GRAY_STACK_FUNCTION_NAME (SgenGrayQueue *queue)
 {
@@ -293,5 +313,9 @@ DRAIN_GRAY_STACK_FUNCTION_NAME (SgenGrayQueue *queue)
 
 #undef COPY_OR_MARK_FUNCTION_NAME
 #undef COPY_OR_MARK_WITH_EVACUATION
+#undef COPY_OR_MARK_CONCURRENT
+#undef COPY_OR_MARK_CONCURRENT_WITH_EVACUATION
 #undef SCAN_OBJECT_FUNCTION_NAME
+#undef SCAN_VTYPE_FUNCTION_NAME
+#undef SCAN_PTR_FIELD_FUNCTION_NAME
 #undef DRAIN_GRAY_STACK_FUNCTION_NAME
diff --git a/mono/sgen/sgen-marksweep-scan-object-concurrent.h b/mono/sgen/sgen-marksweep-scan-object-concurrent.h
deleted file mode 100644 (file)
index 541a0a2..0000000
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * sgen-major-scan-object.h: Object scanning in the major collectors.
- *
- * Copyright 2001-2003 Ximian, Inc
- * Copyright 2003-2010 Novell, Inc.
- * Copyright (C) 2012 Xamarin Inc
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
- */
-
-/*
- * FIXME: We use the same scanning function in the concurrent collector whether we scan
- * during the starting/finishing collection pause (with the world stopped) or from the
- * concurrent worker thread.
- *
- * As long as the world is stopped, we should just follow pointers into the nursery and
- * evict if possible.  In that case we also don't need the ALWAYS_ADD_TO_GLOBAL_REMSET case,
- * which only seems to make sense for when the world is stopped, in which case we only need
- * it because we don't follow into the nursery.
- */
-
-#undef HANDLE_PTR
-#define HANDLE_PTR(ptr,obj)     do {                                    \
-                GCObject *__old = *(ptr);                                   \
-                binary_protocol_scan_process_reference ((full_object), (ptr), __old); \
-                if (__old) {                                            \
-                        gboolean __still_in_nursery = major_copy_or_mark_object_with_evacuation ((ptr), __old, queue); \
-                        if (G_UNLIKELY (__still_in_nursery && !sgen_ptr_in_nursery ((ptr)) && !SGEN_OBJECT_IS_CEMENTED (*(ptr)))) { \
-                                GCObject *__copy = *(ptr);                  \
-                                sgen_add_to_global_remset ((ptr), __copy); \
-                        }                                              \
-                }                                                       \
-        } while (0)
-
-
-static void
-major_scan_vtype_concurrent_finish (GCObject *full_object, char *start, SgenDescriptor desc, SgenGrayQueue *queue BINARY_PROTOCOL_ARG (size_t size))
-{
-       SGEN_OBJECT_LAYOUT_STATISTICS_DECLARE_BITMAP;
-
-#ifdef HEAVY_STATISTICS
-       /* FIXME: We're half scanning this object.  How do we account for that? */
-       //add_scanned_object (start);
-#endif
-
-       /* The descriptors include info about the object header as well */
-       start -= SGEN_CLIENT_OBJECT_HEADER_SIZE;
-
-#define SCAN_OBJECT_NOVTABLE
-#define SCAN_OBJECT_PROTOCOL
-#include "sgen-scan-object.h"
-
-       SGEN_OBJECT_LAYOUT_STATISTICS_COMMIT_BITMAP;
-}
index 7aaaa0221e1d900931d9f052314379a3a00271e5..4c63191ad447d0ea5c9fb76bf44f9eba3ee19b46 100644 (file)
@@ -7,18 +7,7 @@
  * Copyright 2009-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
 #include "mono/sgen/sgen-memory-governor.h"
 #include "mono/sgen/sgen-layout-stats.h"
 #include "mono/sgen/sgen-pointer-queue.h"
+#include "mono/sgen/sgen-array-list.h"
 #include "mono/sgen/sgen-pinning.h"
 #include "mono/sgen/sgen-workers.h"
 #include "mono/sgen/sgen-thread-pool.h"
 #include "mono/sgen/sgen-client.h"
-#include "mono/utils/mono-membar.h"
+#include "mono/utils/mono-memory-model.h"
 
 #if defined(ARCH_MIN_MS_BLOCK_SIZE) && defined(ARCH_MIN_MS_BLOCK_SIZE_SHIFT)
 #define MS_BLOCK_SIZE  ARCH_MIN_MS_BLOCK_SIZE
@@ -109,6 +99,7 @@ struct _MSBlockInfo {
        guint16 obj_size_index;
        /* FIXME: Reduce this - it only needs a byte. */
        volatile gint32 state;
+       gint16 nused;
        unsigned int pinned : 1;
        unsigned int has_references : 1;
        unsigned int has_pinned : 1;    /* means cannot evacuate */
@@ -171,7 +162,7 @@ static int fast_block_obj_size_indexes [MS_NUM_FAST_BLOCK_OBJ_SIZE_INDEXES];
 static gboolean *evacuate_block_obj_sizes;
 static float evacuation_threshold = 0.666f;
 
-static gboolean lazy_sweep = FALSE;
+static gboolean lazy_sweep = TRUE;
 
 enum {
        SWEEP_STATE_SWEPT,
@@ -197,27 +188,25 @@ static gboolean concurrent_sweep = TRUE;
 #define BLOCK_TAG(bl)                          ((bl)->has_references ? BLOCK_TAG_HAS_REFERENCES ((bl)) : (bl))
 
 /* all allocated blocks in the system */
-static SgenPointerQueue allocated_blocks;
+static SgenArrayList allocated_blocks = SGEN_ARRAY_LIST_INIT (NULL, NULL, NULL, INTERNAL_MEM_PIN_QUEUE);
 
 /* non-allocated block free-list */
 static void *empty_blocks = NULL;
 static size_t num_empty_blocks = 0;
 
-#define FOREACH_BLOCK_NO_LOCK_CONDITION(cond,bl) {                     \
-       size_t __index;                                                 \
-       SGEN_ASSERT (0, (cond) && !sweep_in_progress (), "Can't iterate blocks while the world is running or sweep is in progress."); \
-       for (__index = 0; __index < allocated_blocks.next_slot; ++__index) { \
-               (bl) = BLOCK_UNTAG (allocated_blocks.data [__index]);
-#define FOREACH_BLOCK_NO_LOCK(bl)                                      \
-       FOREACH_BLOCK_NO_LOCK_CONDITION(sgen_is_world_stopped (), bl)
+#define FOREACH_BLOCK_NO_LOCK(bl) {                                    \
+       volatile gpointer *slot;                                                \
+       SGEN_ASSERT (0, !sweep_in_progress (), "Can't iterate blocks while sweep is in progress."); \
+       SGEN_ARRAY_LIST_FOREACH_SLOT (&allocated_blocks, slot) {        \
+               (bl) = BLOCK_UNTAG (*slot);
 #define FOREACH_BLOCK_HAS_REFERENCES_NO_LOCK(bl,hr) {                  \
-       size_t __index;                                                 \
-       SGEN_ASSERT (0, sgen_is_world_stopped () && !sweep_in_progress (), "Can't iterate blocks while the world is running or sweep is in progress."); \
-       for (__index = 0; __index < allocated_blocks.next_slot; ++__index) { \
-               (bl) = (MSBlockInfo *)allocated_blocks.data [__index];                  \
+       volatile gpointer *slot;                                                \
+       SGEN_ASSERT (0, !sweep_in_progress (), "Can't iterate blocks while sweep is in progress."); \
+       SGEN_ARRAY_LIST_FOREACH_SLOT (&allocated_blocks, slot) {        \
+               (bl) = (MSBlockInfo *) (*slot);                 \
                (hr) = BLOCK_IS_TAGGED_HAS_REFERENCES ((bl));           \
                (bl) = BLOCK_UNTAG ((bl));
-#define END_FOREACH_BLOCK_NO_LOCK      } }
+#define END_FOREACH_BLOCK_NO_LOCK      } SGEN_ARRAY_LIST_END_FOREACH_SLOT; }
 
 static volatile size_t num_major_sections = 0;
 /*
@@ -386,11 +375,14 @@ ms_get_empty_block (void)
  * list, where it will either be freed later on, or reused in nursery collections.
  */
 static void
-ms_free_block (void *block)
+ms_free_block (MSBlockInfo *info)
 {
        void *empty;
+       char *block = MS_BLOCK_FOR_BLOCK_INFO (info);
 
        sgen_memgov_release_space (MS_BLOCK_SIZE, SPACE_MAJOR);
+       if (info->cardtable_mod_union)
+               sgen_card_table_free_mod_union (info->cardtable_mod_union, block, MS_BLOCK_SIZE);
        memset (block, 0, MS_BLOCK_SIZE);
 
        do {
@@ -436,7 +428,7 @@ check_block_free_list (MSBlockInfo *block, int size, gboolean pinned)
                g_assert (block->free_list);
 
                /* the block must be in the allocated_blocks array */
-               g_assert (sgen_pointer_queue_find (&allocated_blocks, BLOCK_TAG (block)) != (size_t)-1);
+               g_assert (sgen_array_list_find (&allocated_blocks, BLOCK_TAG (block)) != (guint32)-1);
        }
 }
 
@@ -567,7 +559,7 @@ ms_alloc_block (int size_index, gboolean pinned, gboolean has_references)
        major_finish_sweep_checking ();
        mono_memory_barrier ();
 
-       sgen_pointer_queue_add (&allocated_blocks, BLOCK_TAG (info));
+       sgen_array_list_add (&allocated_blocks, BLOCK_TAG (info), 0, FALSE);
 
        SGEN_ATOMIC_ADD_P (num_major_sections, 1);
        return TRUE;
@@ -815,14 +807,15 @@ set_sweep_state (int new_, int expected)
        SGEN_ASSERT (0, success, "Could not set sweep state.");
 }
 
-static gboolean ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *have_checked);
+static gboolean ensure_block_is_checked_for_sweeping (guint32 block_index, gboolean wait, gboolean *have_checked);
 
 static SgenThreadPoolJob * volatile sweep_job;
+static SgenThreadPoolJob * volatile sweep_blocks_job;
 
 static void
 major_finish_sweep_checking (void)
 {
-       int block_index;
+       guint32 block_index;
        SgenThreadPoolJob *job;
 
  retry:
@@ -1076,7 +1069,6 @@ mark_mod_union_card (GCObject *obj, void **ptr, GCObject *value_obj)
        } else {
                sgen_los_mark_mod_union_card (obj, ptr);
        }
-
        binary_protocol_mod_union_remset (obj, ptr, value_obj, SGEN_LOAD_VTABLE (value_obj));
 }
 
@@ -1185,20 +1177,22 @@ static guint64 stat_drain_loops;
 #define COPY_OR_MARK_WITH_EVACUATION
 #define COPY_OR_MARK_FUNCTION_NAME     major_copy_or_mark_object_with_evacuation
 #define SCAN_OBJECT_FUNCTION_NAME      major_scan_object_with_evacuation
+#define SCAN_VTYPE_FUNCTION_NAME       major_scan_vtype_with_evacuation
 #define DRAIN_GRAY_STACK_FUNCTION_NAME drain_gray_stack_with_evacuation
+#define SCAN_PTR_FIELD_FUNCTION_NAME   major_scan_ptr_field_with_evacuation
 #include "sgen-marksweep-drain-gray-stack.h"
 
-#undef COPY_OR_MARK_WITH_EVACUATION
 #define COPY_OR_MARK_CONCURRENT
 #define COPY_OR_MARK_FUNCTION_NAME     major_copy_or_mark_object_concurrent_no_evacuation
 #define SCAN_OBJECT_FUNCTION_NAME      major_scan_object_concurrent_no_evacuation
 #define DRAIN_GRAY_STACK_FUNCTION_NAME drain_gray_stack_concurrent_no_evacuation
 #include "sgen-marksweep-drain-gray-stack.h"
 
-#undef COPY_OR_MARK_CONCURRENT
 #define COPY_OR_MARK_CONCURRENT_WITH_EVACUATION
 #define COPY_OR_MARK_FUNCTION_NAME     major_copy_or_mark_object_concurrent_with_evacuation
 #define SCAN_OBJECT_FUNCTION_NAME      major_scan_object_concurrent_with_evacuation
+#define SCAN_VTYPE_FUNCTION_NAME       major_scan_vtype_concurrent_with_evacuation
+#define SCAN_PTR_FIELD_FUNCTION_NAME   major_scan_ptr_field_concurrent_with_evacuation
 #define DRAIN_GRAY_STACK_FUNCTION_NAME drain_gray_stack_concurrent_with_evacuation
 #include "sgen-marksweep-drain-gray-stack.h"
 
@@ -1233,8 +1227,6 @@ drain_gray_stack_concurrent (SgenGrayQueue *queue)
                return drain_gray_stack_concurrent_no_evacuation (queue);
 }
 
-#include "sgen-marksweep-scan-object-concurrent.h"
-
 static void
 major_copy_or_mark_object_canonical (GCObject **ptr, SgenGrayQueue *queue)
 {
@@ -1449,7 +1441,7 @@ static void sweep_finish (void);
  * be correct, i.e. must not be used.
  */
 static gboolean
-ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *have_checked)
+ensure_block_is_checked_for_sweeping (guint32 block_index, gboolean wait, gboolean *have_checked)
 {
        int count;
        gboolean have_live = FALSE;
@@ -1459,6 +1451,7 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
        int i;
        void *tagged_block;
        MSBlockInfo *block;
+       volatile gpointer *block_slot = sgen_array_list_get_slot (&allocated_blocks, block_index);
 
        SGEN_ASSERT (6, sweep_in_progress (), "Why do we call this function if there's no sweep in progress?");
 
@@ -1466,7 +1459,7 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
                *have_checked = FALSE;
 
  retry:
-       tagged_block = *(void * volatile *)&allocated_blocks.data [block_index];
+       tagged_block = *(void * volatile *)block_slot;
        if (!tagged_block)
                return FALSE;
 
@@ -1478,7 +1471,7 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
                goto retry;
        }
 
-       if (SGEN_CAS_PTR (&allocated_blocks.data [block_index], BLOCK_TAG_CHECKING (tagged_block), tagged_block) != tagged_block)
+       if (SGEN_CAS_PTR (block_slot, BLOCK_TAG_CHECKING (tagged_block), tagged_block) != tagged_block)
                goto retry;
 
        block = BLOCK_UNTAG (tagged_block);
@@ -1517,15 +1510,14 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
 
        count = MS_BLOCK_FREE / block->obj_size;
 
-       if (block->cardtable_mod_union) {
-               sgen_card_table_free_mod_union (block->cardtable_mod_union, MS_BLOCK_FOR_BLOCK_INFO (block), MS_BLOCK_SIZE);
-               block->cardtable_mod_union = NULL;
-       }
+       if (block->cardtable_mod_union)
+               memset (block->cardtable_mod_union, 0, CARDS_PER_BLOCK);
 
        /* Count marked objects in the block */
        for (i = 0; i < MS_NUM_MARK_WORDS; ++i)
                nused += bitcount (block->mark_words [i]);
 
+       block->nused = nused;
        if (nused)
                have_live = TRUE;
        if (nused < count)
@@ -1572,7 +1564,7 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
                 * block list and freed.
                 */
                SGEN_ASSERT (6, block_index < allocated_blocks.next_slot, "How did the number of blocks shrink?");
-               SGEN_ASSERT (6, allocated_blocks.data [block_index] == BLOCK_TAG_CHECKING (tagged_block), "How did the block move?");
+               SGEN_ASSERT (6, *block_slot == BLOCK_TAG_CHECKING (tagged_block), "How did the block move?");
 
                binary_protocol_empty (MS_BLOCK_OBJ (block, 0), (char*)MS_BLOCK_OBJ (block, count) - (char*)MS_BLOCK_OBJ (block, 0));
                ms_free_block (block);
@@ -1583,15 +1575,29 @@ ensure_block_is_checked_for_sweeping (int block_index, gboolean wait, gboolean *
        }
 
  done:
-       allocated_blocks.data [block_index] = tagged_block;
+       *block_slot = tagged_block;
        return !!tagged_block;
 }
 
+static void
+sweep_blocks_job_func (void *thread_data_untyped, SgenThreadPoolJob *job)
+{
+       volatile gpointer *slot;
+
+       SGEN_ARRAY_LIST_FOREACH_SLOT (&allocated_blocks, slot) {
+               sweep_block (BLOCK_UNTAG (*slot));
+       } SGEN_ARRAY_LIST_END_FOREACH_SLOT;
+
+       mono_memory_write_barrier ();
+
+       sweep_blocks_job = NULL;
+}
+
 static void
 sweep_job_func (void *thread_data_untyped, SgenThreadPoolJob *job)
 {
-       int block_index;
-       int num_blocks = num_major_sections_before_sweep;
+       guint32 block_index;
+       guint32 num_blocks = num_major_sections_before_sweep;
 
        SGEN_ASSERT (0, sweep_in_progress (), "Sweep thread called with wrong state");
        SGEN_ASSERT (0, num_blocks <= allocated_blocks.next_slot, "How did we lose blocks?");
@@ -1601,14 +1607,12 @@ sweep_job_func (void *thread_data_untyped, SgenThreadPoolJob *job)
         * cooperate with the sweep thread to finish sweeping, and they will traverse from
         * low to high, to avoid constantly colliding on the same blocks.
         */
-       for (block_index = num_blocks - 1; block_index >= 0; --block_index) {
-               gboolean have_checked;
-
+       for (block_index = num_blocks; block_index-- > 0;) {
                /*
                 * The block might have been freed by another thread doing some checking
                 * work.
                 */
-               if (!ensure_block_is_checked_for_sweeping (block_index, TRUE, &have_checked))
+               if (!ensure_block_is_checked_for_sweeping (block_index, TRUE, NULL))
                        ++num_major_sections_freed_in_sweep;
        }
 
@@ -1623,13 +1627,22 @@ sweep_job_func (void *thread_data_untyped, SgenThreadPoolJob *job)
 
        if (SGEN_MAX_ASSERT_LEVEL >= 6) {
                for (block_index = num_blocks; block_index < allocated_blocks.next_slot; ++block_index) {
-                       MSBlockInfo *block = BLOCK_UNTAG (allocated_blocks.data [block_index]);
+                       MSBlockInfo *block = BLOCK_UNTAG (*sgen_array_list_get_slot (&allocated_blocks, block_index));
                        SGEN_ASSERT (6, block && block->state == BLOCK_STATE_SWEPT, "How did a new block to be swept get added while swept?");
                }
        }
 
-       sgen_pointer_queue_remove_nulls (&allocated_blocks);
-       mono_memory_barrier ();
+       sgen_array_list_remove_nulls (&allocated_blocks);
+
+       /*
+        * Concurrently sweep all the blocks to reduce workload during minor
+        * pauses where we need certain blocks to be swept. At the start of
+        * the next major we need all blocks to be swept anyway.
+        */
+       if (concurrent_sweep && lazy_sweep) {
+               sweep_blocks_job = sgen_thread_pool_job_alloc ("sweep_blocks", sweep_blocks_job_func, sizeof (SgenThreadPoolJob));
+               sgen_thread_pool_job_enqueue (sweep_blocks_job);
+       }
 
        sweep_finish ();
 
@@ -1654,7 +1667,11 @@ sweep_finish (void)
                }
        }
 
+       sgen_memgov_major_post_sweep ();
+
        set_sweep_state (SWEEP_STATE_SWEPT, SWEEP_STATE_COMPACTING);
+       if (concurrent_sweep)
+               binary_protocol_concurrent_sweep_end (sgen_timestamp ());
 }
 
 static void
@@ -1791,6 +1808,67 @@ major_finish_nursery_collection (void)
 #endif
 }
 
+static int
+block_usage_comparer (const void *bl1, const void *bl2)
+{
+       const gint16 nused1 = (*(MSBlockInfo**)bl1)->nused;
+       const gint16 nused2 = (*(MSBlockInfo**)bl2)->nused;
+
+       return nused2 - nused1;
+}
+
+static void
+sgen_evacuation_freelist_blocks (MSBlockInfo * volatile *block_list, int size_index)
+{
+       MSBlockInfo **evacuated_blocks;
+       size_t index = 0, count, num_blocks = 0, num_used = 0;
+       MSBlockInfo *info;
+       MSBlockInfo * volatile *prev;
+
+       for (info = *block_list; info != NULL; info = info->next_free) {
+               num_blocks++;
+               num_used += info->nused;
+       }
+
+       /*
+        * We have a set of blocks in the freelist which will be evacuated. Instead
+        * of evacuating all of the blocks into new ones, we traverse the freelist
+        * sorting it by the number of occupied slots, evacuating the objects from
+        * blocks with fewer used slots into fuller blocks.
+        *
+        * The number of used slots is set at the end of the previous sweep. Since
+        * we sequentially unlink slots from blocks, except for the head of the
+        * freelist, for blocks on the freelist, the number of used slots is the same
+        * as at the end of the previous sweep.
+        */
+       evacuated_blocks = (MSBlockInfo**)sgen_alloc_internal_dynamic (sizeof (MSBlockInfo*) * num_blocks, INTERNAL_MEM_TEMPORARY, TRUE);
+
+       for (info = *block_list; info != NULL; info = info->next_free) {
+               evacuated_blocks [index++] = info;
+       }
+
+       SGEN_ASSERT (0, num_blocks == index, "Why did the freelist change ?");
+
+       qsort (evacuated_blocks, num_blocks, sizeof (gpointer), block_usage_comparer);
+
+       /*
+        * Form a new freelist with the fullest blocks. These blocks will also be
+        * marked as to_space so we don't evacuate from them.
+        */
+       count = MS_BLOCK_FREE / block_obj_sizes [size_index];
+       prev = block_list;
+       for (index = 0; index < (num_used + count - 1) / count; index++) {
+               SGEN_ASSERT (0, index < num_blocks, "Why do we need more blocks for compaction than we already had ?");
+               info = evacuated_blocks [index];
+               info->is_to_space = TRUE;
+               *prev = info;
+               prev = &info->next_free;
+       }
+       *prev = NULL;
+
+       sgen_free_internal_dynamic (evacuated_blocks, sizeof (MSBlockInfo*) * num_blocks, INTERNAL_MEM_TEMPORARY);
+}
+
 static void
 major_start_major_collection (void)
 {
@@ -1809,22 +1887,38 @@ major_start_major_collection (void)
 
                binary_protocol_evacuating_blocks (block_obj_sizes [i]);
 
-               free_block_lists [0][i] = NULL;
-               free_block_lists [MS_BLOCK_FLAG_REFS][i] = NULL;
+               sgen_evacuation_freelist_blocks (&free_block_lists [0][i], i);
+               sgen_evacuation_freelist_blocks (&free_block_lists [MS_BLOCK_FLAG_REFS][i], i);
        }
 
-       if (lazy_sweep)
-               binary_protocol_sweep_begin (GENERATION_OLD, TRUE);
+       if (lazy_sweep && concurrent_sweep) {
+               /*
+                * sweep_blocks_job is created before sweep_finish, which we wait for above
+                * (major_finish_sweep_checking). After the end of sweep, if we don't have
+                * sweep_blocks_job set, it means that it has already been run.
+                */
+               SgenThreadPoolJob *job = sweep_blocks_job;
+               if (job)
+                       sgen_thread_pool_job_wait (job);
+       }
 
+       if (lazy_sweep && !concurrent_sweep)
+               binary_protocol_sweep_begin (GENERATION_OLD, TRUE);
        /* Sweep all unswept blocks and set them to MARKING */
        FOREACH_BLOCK_NO_LOCK (block) {
-               if (lazy_sweep)
+               if (lazy_sweep && !concurrent_sweep)
                        sweep_block (block);
                SGEN_ASSERT (0, block->state == BLOCK_STATE_SWEPT, "All blocks must be swept when we're pinning.");
                set_block_state (block, BLOCK_STATE_MARKING, BLOCK_STATE_SWEPT);
+               /*
+                * Swept blocks that have a null free_list are full. Evacuation is not
+                * effective on these blocks since we expect them to have high usage anyway,
+                * given that the survival rate for majors is relatively high.
+                */
+               if (evacuate_block_obj_sizes [block->obj_size_index] && !block->free_list)
+                       block->is_to_space = TRUE;
        } END_FOREACH_BLOCK_NO_LOCK;
-
-       if (lazy_sweep)
+       if (lazy_sweep && !concurrent_sweep)
                binary_protocol_sweep_end (GENERATION_OLD, TRUE);
 
        set_sweep_state (SWEEP_STATE_NEED_SWEEPING, SWEEP_STATE_SWEPT);
@@ -2052,7 +2146,7 @@ major_get_used_size (void)
         */
        major_finish_sweep_checking ();
 
-       FOREACH_BLOCK_NO_LOCK_CONDITION (TRUE, block) {
+       FOREACH_BLOCK_NO_LOCK (block) {
                int count = MS_BLOCK_FREE / block->obj_size;
                void **iter;
                size += count * block->obj_size;
@@ -2186,13 +2280,14 @@ initial_skip_card (guint8 *card_data)
 #define MS_OBJ_ALLOCED_FAST(o,b)               (*(void**)(o) && (*(char**)(o) < (b) || *(char**)(o) >= (b) + MS_BLOCK_SIZE))
 
 static void
-scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyContext ctx)
+scan_card_table_for_block (MSBlockInfo *block, CardTableScanType scan_type, ScanCopyContext ctx)
 {
        SgenGrayQueue *queue = ctx.queue;
        ScanObjectFunc scan_func = ctx.ops->scan_object;
 #ifndef SGEN_HAVE_OVERLAPPING_CARDS
        guint8 cards_copy [CARDS_PER_BLOCK];
 #endif
+       guint8 cards_preclean [CARDS_PER_BLOCK];
        gboolean small_objects;
        int block_obj_size;
        char *block_start;
@@ -2200,6 +2295,10 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
        guint8 *card_data_end;
        char *scan_front = NULL;
 
+       /* The concurrent mark doesn't enter evacuating blocks */
+       if (scan_type == CARDTABLE_SCAN_MOD_UNION_PRECLEAN && major_block_is_evacuating (block))
+               return;
+
        block_obj_size = block->obj_size;
        small_objects = block_obj_size < CARD_SIZE_IN_BYTES;
 
@@ -2212,7 +2311,7 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
         * Cards aliasing happens in powers of two, so as long as major blocks are aligned to their
         * sizes, they won't overflow the cardtable overlap modulus.
         */
-       if (mod_union) {
+       if (scan_type & CARDTABLE_SCAN_MOD_UNION) {
                card_data = card_base = block->cardtable_mod_union;
                /*
                 * This happens when the nursery collection that precedes finishing
@@ -2220,6 +2319,11 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
                 */
                if (!card_data)
                        return;
+
+               if (scan_type == CARDTABLE_SCAN_MOD_UNION_PRECLEAN) {
+                       sgen_card_table_preclean_mod_union (card_data, cards_preclean, CARDS_PER_BLOCK);
+                       card_data = card_base = cards_preclean;
+               }
        } else {
 #ifdef SGEN_HAVE_OVERLAPPING_CARDS
                card_data = card_base = sgen_card_table_get_card_scan_address ((mword)block_start);
@@ -2278,7 +2382,7 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
                        if (obj < scan_front || !MS_OBJ_ALLOCED_FAST (obj, block_start))
                                goto next_object;
 
-                       if (mod_union) {
+                       if (scan_type & CARDTABLE_SCAN_MOD_UNION) {
                                /* FIXME: do this more efficiently */
                                int w, b;
                                MS_CALC_MARK_BIT (w, b, obj);
@@ -2293,7 +2397,7 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
                                scan_func (object, sgen_obj_get_descriptor (object), queue);
                        } else {
                                size_t offset = sgen_card_table_get_card_offset (obj, block_start);
-                               sgen_cardtable_scan_object (object, block_obj_size, card_base + offset, mod_union, ctx);
+                               sgen_cardtable_scan_object (object, block_obj_size, card_base + offset, ctx);
                        }
                next_object:
                        obj += block_obj_size;
@@ -2311,34 +2415,36 @@ scan_card_table_for_block (MSBlockInfo *block, gboolean mod_union, ScanCopyConte
 }
 
 static void
-major_scan_card_table (gboolean mod_union, ScanCopyContext ctx)
+major_scan_card_table (CardTableScanType scan_type, ScanCopyContext ctx)
 {
        MSBlockInfo *block;
        gboolean has_references;
 
        if (!concurrent_mark)
-               g_assert (!mod_union);
+               g_assert (scan_type == CARDTABLE_SCAN_GLOBAL);
 
        major_finish_sweep_checking ();
-       binary_protocol_major_card_table_scan_start (sgen_timestamp (), mod_union);
+       binary_protocol_major_card_table_scan_start (sgen_timestamp (), scan_type & CARDTABLE_SCAN_MOD_UNION);
        FOREACH_BLOCK_HAS_REFERENCES_NO_LOCK (block, has_references) {
 #ifdef PREFETCH_CARDS
                int prefetch_index = __index + 6;
                if (prefetch_index < allocated_blocks.next_slot) {
-                       MSBlockInfo *prefetch_block = BLOCK_UNTAG (allocated_blocks.data [prefetch_index]);
-                       guint8 *prefetch_cards = sgen_card_table_get_card_scan_address ((mword)MS_BLOCK_FOR_BLOCK_INFO (prefetch_block));
+                       MSBlockInfo *prefetch_block = BLOCK_UNTAG (*sgen_array_list_get_slot (&allocated_blocks, prefetch_index));
                        PREFETCH_READ (prefetch_block);
-                       PREFETCH_WRITE (prefetch_cards);
-                       PREFETCH_WRITE (prefetch_cards + 32);
+                       if (scan_type == CARDTABLE_SCAN_GLOBAL) {
+                               guint8 *prefetch_cards = sgen_card_table_get_card_scan_address ((mword)MS_BLOCK_FOR_BLOCK_INFO (prefetch_block));
+                               PREFETCH_WRITE (prefetch_cards);
+                               PREFETCH_WRITE (prefetch_cards + 32);
+                       }
                 }
 #endif
 
                if (!has_references)
                        continue;
 
-               scan_card_table_for_block (block, mod_union, ctx);
+               scan_card_table_for_block (block, scan_type, ctx);
        } END_FOREACH_BLOCK_NO_LOCK;
-       binary_protocol_major_card_table_scan_end (sgen_timestamp (), mod_union);
+       binary_protocol_major_card_table_scan_end (sgen_timestamp (), scan_type & CARDTABLE_SCAN_MOD_UNION);
 }
 
 static void
@@ -2379,10 +2485,21 @@ update_cardtable_mod_union (void)
        MSBlockInfo *block;
 
        FOREACH_BLOCK_NO_LOCK (block) {
-               size_t num_cards;
-               guint8 *mod_union = get_cardtable_mod_union_for_block (block, TRUE);
-               sgen_card_table_update_mod_union (mod_union, MS_BLOCK_FOR_BLOCK_INFO (block), MS_BLOCK_SIZE, &num_cards);
-               SGEN_ASSERT (6, num_cards == CARDS_PER_BLOCK, "Number of cards calculation is wrong");
+               gpointer *card_start = (gpointer*) sgen_card_table_get_card_address ((mword)MS_BLOCK_FOR_BLOCK_INFO (block));
+               gboolean has_dirty_cards = FALSE;
+               int i;
+               for (i = 0; i < CARDS_PER_BLOCK / sizeof(gpointer); i++) {
+                       if (card_start [i]) {
+                               has_dirty_cards = TRUE;
+                               break;
+                       }
+               }
+               if (has_dirty_cards) {
+                       size_t num_cards;
+                       guint8 *mod_union = get_cardtable_mod_union_for_block (block, TRUE);
+                       sgen_card_table_update_mod_union (mod_union, MS_BLOCK_FOR_BLOCK_INFO (block), MS_BLOCK_SIZE, &num_cards);
+                       SGEN_ASSERT (6, num_cards == CARDS_PER_BLOCK, "Number of cards calculation is wrong");
+               }
        } END_FOREACH_BLOCK_NO_LOCK;
 }
 
@@ -2496,11 +2613,14 @@ sgen_marksweep_init_internal (SgenMajorCollector *collector, gboolean is_concurr
        if (is_concurrent) {
                collector->major_ops_concurrent_start.copy_or_mark_object = major_copy_or_mark_object_concurrent_canonical;
                collector->major_ops_concurrent_start.scan_object = major_scan_object_concurrent_with_evacuation;
+               collector->major_ops_concurrent_start.scan_vtype = major_scan_vtype_concurrent_with_evacuation;
+               collector->major_ops_concurrent_start.scan_ptr_field = major_scan_ptr_field_concurrent_with_evacuation;
                collector->major_ops_concurrent_start.drain_gray_stack = drain_gray_stack_concurrent;
 
                collector->major_ops_concurrent_finish.copy_or_mark_object = major_copy_or_mark_object_concurrent_finish_canonical;
                collector->major_ops_concurrent_finish.scan_object = major_scan_object_with_evacuation;
-               collector->major_ops_concurrent_finish.scan_vtype = major_scan_vtype_concurrent_finish;
+               collector->major_ops_concurrent_finish.scan_vtype = major_scan_vtype_with_evacuation;
+               collector->major_ops_concurrent_finish.scan_ptr_field = major_scan_ptr_field_with_evacuation;
                collector->major_ops_concurrent_finish.drain_gray_stack = drain_gray_stack;
        }
 
index 611ae5c118f4d66b7e1eb982fd4d32048e78a20b..7415ce3bff1b3ce63468582f8e1d4cc888e0fc3c 100644 (file)
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -189,6 +178,17 @@ sgen_memgov_major_pre_sweep (void)
        }
 }
 
+void
+sgen_memgov_major_post_sweep (void)
+{
+       mword num_major_sections = major_collector.get_num_major_sections ();
+
+       mono_trace (G_LOG_LEVEL_INFO, MONO_TRACE_GC, "GC_MAJOR_SWEEP: major %dK/%dK",
+               num_major_sections * major_collector.section_size / 1024,
+               last_major_num_sections * major_collector.section_size / 1024);
+       last_major_num_sections = num_major_sections;
+}
+
 void
 sgen_memgov_major_collection_start (void)
 {
@@ -224,7 +224,7 @@ sgen_memgov_collection_end (int generation, GGTimingInfo* info, int info_count)
                if (info[i].generation != -1)
                        sgen_client_log_timing (&info [i], last_major_num_sections, last_los_memory_usage);
        }
-       last_major_num_sections = major_collector.get_num_major_sections ();
+       last_los_memory_usage = los_memory_usage;
 }
 
 /*
index 669b59734e99200ffadae2dc540a7b8137f6349c..9bcd55b4d80ad157417567512f7363438029f468 100644 (file)
@@ -2,24 +2,7 @@
  * Copyright 2001-2003 Ximian, Inc
  * Copyright 2003-2010 Novell, Inc.
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_MEMORY_GOVERNOR_H__
 #define __MONO_SGEN_MEMORY_GOVERNOR_H__
@@ -34,6 +17,7 @@ void sgen_memgov_minor_collection_start (void);
 void sgen_memgov_minor_collection_end (void);
 
 void sgen_memgov_major_pre_sweep (void);
+void sgen_memgov_major_post_sweep (void);
 void sgen_memgov_major_collection_start (void);
 void sgen_memgov_major_collection_end (gboolean forced);
 
index 49b42265c7a7d4076c214b5c80f55a8634e248af..a77d53b4744bed22af7beefdba02232bbb373c22 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #define collector_pin_object(obj, queue) sgen_pin_object (obj, queue);
index b1895985dc34e340f32093abfb423f967711f44a..4b62a739f27183622a0dbc4441e1ea2b17536b9c 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 extern guint64 stat_scan_object_called_nursery;
@@ -80,7 +69,14 @@ SERIAL_SCAN_VTYPE (GCObject *full_object, char *start, SgenDescriptor desc, Sgen
 #include "sgen-scan-object.h"
 }
 
+static void
+SERIAL_SCAN_PTR_FIELD (GCObject *full_object, GCObject **ptr, SgenGrayQueue *queue)
+{
+       HANDLE_PTR (ptr, NULL);
+}
+
 #define FILL_MINOR_COLLECTOR_SCAN_OBJECT(collector)    do {                    \
                (collector)->serial_ops.scan_object = SERIAL_SCAN_OBJECT;       \
                (collector)->serial_ops.scan_vtype = SERIAL_SCAN_VTYPE; \
+               (collector)->serial_ops.scan_ptr_field = SERIAL_SCAN_PTR_FIELD; \
        } while (0)
index e42e3bf64aa75efc7001025dbb4a124c254d0576..785f46d5645c183043c8f09d047f4f2f3e7efeca 100644 (file)
@@ -7,18 +7,7 @@
  * Copyright 2011 Xamarin Inc  (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index 5edccfaabec10720fcb6658f1eb8e7d54b8ccc24..26fcfd116af32464cb5d01bcb1a6573144c5082e 100644 (file)
@@ -3,24 +3,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * 
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index a94af9ddf4494db961697faac801a9273bece46b..cfe3db1acd0167bd08d1c7e285b6313736460ec3 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
 
 static SgenPointerQueue pin_queue;
 static size_t last_num_pinned = 0;
+/*
+ * While we hold the pin_queue_mutex, all objects in pin_queue_objs will
+ * stay pinned, which means they can't move, therefore they can be scanned.
+ */
+static SgenPointerQueue pin_queue_objs;
+static MonoCoopMutex pin_queue_mutex;
 
 #define PIN_HASH_SIZE 1024
 static void *pin_hash_filter [PIN_HASH_SIZE];
 
+void
+sgen_pinning_init (void)
+{
+       mono_coop_mutex_init (&pin_queue_mutex);
+}
+
 void
 sgen_init_pinning (void)
 {
+       mono_coop_mutex_lock (&pin_queue_mutex);
        memset (pin_hash_filter, 0, sizeof (pin_hash_filter));
        pin_queue.mem_type = INTERNAL_MEM_PIN_QUEUE;
+       sgen_pointer_queue_clear (&pin_queue_objs);
 }
 
 void
@@ -48,6 +51,27 @@ sgen_finish_pinning (void)
 {
        last_num_pinned = pin_queue.next_slot;
        sgen_pointer_queue_clear (&pin_queue);
+       mono_coop_mutex_unlock (&pin_queue_mutex);
+}
+
+void
+sgen_pinning_register_pinned_in_nursery (GCObject *obj)
+{
+       sgen_pointer_queue_add (&pin_queue_objs, obj);
+}
+
+void
+sgen_scan_pin_queue_objects (ScanCopyContext ctx)
+{
+       int i;
+       ScanObjectFunc scan_func = ctx.ops->scan_object;
+
+       mono_coop_mutex_lock (&pin_queue_mutex);
+       for (i = 0; i < pin_queue_objs.next_slot; ++i) {
+               GCObject *obj = (GCObject *)pin_queue_objs.data [i];
+               scan_func (obj, sgen_obj_get_descriptor_safe (obj), ctx.queue);
+       }
+       mono_coop_mutex_unlock (&pin_queue_mutex);
 }
 
 void
@@ -182,6 +206,7 @@ typedef struct _CementHashEntry CementHashEntry;
 struct _CementHashEntry {
        GCObject *obj;
        unsigned int count;
+       gboolean forced; /* if it should stay cemented after the finishing pause */
 };
 
 static CementHashEntry cement_hash [SGEN_CEMENT_HASH_SIZE];
@@ -197,10 +222,70 @@ sgen_cement_init (gboolean enabled)
 void
 sgen_cement_reset (void)
 {
-       memset (cement_hash, 0, sizeof (cement_hash));
+       int i;
+       for (i = 0; i < SGEN_CEMENT_HASH_SIZE; i++) {
+               if (cement_hash [i].forced) {
+                       cement_hash [i].forced = FALSE;
+               } else {
+                       cement_hash [i].obj = NULL;
+                       cement_hash [i].count = 0;
+               }
+       }
        binary_protocol_cement_reset ();
 }
 
+
+/*
+ * The pin_queue should be full and sorted, without entries from the cemented
+ * objects. We traverse the cement hash and check if each object is pinned in
+ * the pin_queue (the pin_queue contains entries between obj and obj+obj_len)
+ */
+void
+sgen_cement_force_pinned (void)
+{
+       int i;
+
+       if (!cement_enabled)
+               return;
+
+       for (i = 0; i < SGEN_CEMENT_HASH_SIZE; i++) {
+               GCObject *obj = cement_hash [i].obj;
+               size_t index;
+               if (!obj)
+                       continue;
+               if (cement_hash [i].count < SGEN_CEMENT_THRESHOLD)
+                       continue;
+               SGEN_ASSERT (0, !cement_hash [i].forced, "Why do we have a forced cemented object before forcing ?");
+
+               /* Returns the index of the target or of the first element greater than it */
+               index = sgen_pointer_queue_search (&pin_queue, obj);
+               if (index == pin_queue.next_slot)
+                       continue;
+               SGEN_ASSERT (0, pin_queue.data [index] >= (gpointer)obj, "Binary search should return a pointer greater than the search target");
+               if (pin_queue.data [index] < (gpointer)((char*)obj + sgen_safe_object_get_size (obj)))
+                       cement_hash [i].forced = TRUE;
+       }
+}
+
+gboolean
+sgen_cement_is_forced (GCObject *obj)
+{
+       guint hv = sgen_aligned_addr_hash (obj);
+       int i = SGEN_CEMENT_HASH (hv);
+
+       SGEN_ASSERT (5, sgen_ptr_in_nursery (obj), "Looking up cementing for non-nursery objects makes no sense");
+
+       if (!cement_enabled)
+               return FALSE;
+
+       if (!cement_hash [i].obj)
+               return FALSE;
+       if (cement_hash [i].obj != obj)
+               return FALSE;
+
+       return cement_hash [i].forced;
+}
+
 gboolean
 sgen_cement_lookup (GCObject *obj)
 {
index e7f1e288f81c42d41e51a565c19eaa4d80a9e38c..2ae2594fa85e1c762898e60d43e6caafaf0ed40a 100644 (file)
@@ -4,18 +4,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGEN_PINNING_H__
 #define __MONO_SGEN_PINNING_H__
@@ -29,10 +18,13 @@ enum {
        PIN_TYPE_MAX
 };
 
+void sgen_pinning_init (void);
 void sgen_pin_stage_ptr (void *ptr);
 void sgen_optimize_pin_queue (void);
 void sgen_init_pinning (void);
 void sgen_finish_pinning (void);
+void sgen_pinning_register_pinned_in_nursery (GCObject *obj);
+void sgen_scan_pin_queue_objects (ScanCopyContext ctx);
 void sgen_pin_queue_clear_discarded_entries (GCMemSection *section, size_t max_pin_slot);
 size_t sgen_get_pinned_count (void);
 void sgen_pinning_setup_section (GCMemSection *section);
@@ -56,6 +48,8 @@ void sgen_pin_stats_reset (void);
 
 void sgen_cement_init (gboolean enabled);
 void sgen_cement_reset (void);
+void sgen_cement_force_pinned (void);
+gboolean sgen_cement_is_forced (GCObject *obj);
 gboolean sgen_cement_lookup (GCObject *obj);
 gboolean sgen_cement_lookup_or_register (GCObject *obj);
 void sgen_pin_cemented_objects (void);
index 196bc3010716ef21708b019d4bddafb2656b4618..5fb25b0bdc53ce85ac6244422f841c6ff645e813 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifdef HAVE_SGEN_GC
index 3352dab3c58f0e308ae9b1b4d3b44526f474b9c4..5127b5bdc1db15038b16213469545ee12d17c76a 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGEN_POINTER_QUEUE_H__
index 8a190ef6f494df314fa590d74a0022af78f28294..3ab36e3bf660f380b9b21cf554f0e659899eb520 100644 (file)
@@ -435,6 +435,13 @@ MATCH_INDEX (BINARY_PROTOCOL_MATCH)
 IS_VTABLE_MATCH (FALSE)
 END_PROTOCOL_ENTRY
 
+BEGIN_PROTOCOL_ENTRY1 (binary_protocol_concurrent_sweep_end, TYPE_LONGLONG, timestamp)
+DEFAULT_PRINT ()
+IS_ALWAYS_MATCH (TRUE)
+MATCH_INDEX (BINARY_PROTOCOL_MATCH)
+IS_VTABLE_MATCH (FALSE)
+END_PROTOCOL_ENTRY
+
 #undef BEGIN_PROTOCOL_ENTRY0
 #undef BEGIN_PROTOCOL_ENTRY1
 #undef BEGIN_PROTOCOL_ENTRY2
index 963035950b32ecdad234e250174df43819e5f02c..ffc47f248de05a2c17a3f93648118bed4e2079ea 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifdef HAVE_SGEN_GC
index 220418e8167deea8101378669fffc325ee38be66..5ec3680fc5a58018a358eaa583afdf9613753ddf 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGENPROTOCOL_H__
index 7566bddbc1d6370ea7c6715c4446b0b1c7fc35be..802dd561e9ed260df85cfd512b843034f9d4fcf1 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2013 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 75577e57122c354f36d195e5ba23e5da3bbfc876..b9d0f648138e4c694eac038b0d3b295001df4270 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_SGENQSORT_H__
 #define __MONO_SGENQSORT_H__
index b7f973646315254877cee62e526435d6f8dcba7b..b5cbedaa92ec50bb9d0b1237e353a244ad4a6303 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2013 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  *
  *
  * Scans one object, using the OBJ_XXX macros.  The start of the
index 40639d7050b1db8d2793aa66cf7156285fe0bb9a..56a235aa30f42473511957269500bc45a86870c1 100644 (file)
@@ -6,18 +6,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 588651fbc0b67965c946fadc800602c16ca05b0d..3606607809e954c2888f1dceae8b70d0ea4cb135 100644 (file)
@@ -9,18 +9,7 @@
  * Copyright 2011-2012 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 2d55abbbcc19839bf2e6348f6a683ffd6c5c123a..8b28fde01707b1b46fa2d5f292400cefca3154fc 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGEN_TAGGED_POINTER_H__
index e9706943f847803dc38b88b633b6464aefe85c75..f1664f6a23fcb7fd727fe533a45cea606d00134b 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -41,6 +30,9 @@ static SgenThreadPoolThreadInitFunc thread_init_func;
 static SgenThreadPoolIdleJobFunc idle_job_func;
 static SgenThreadPoolContinueIdleJobFunc continue_idle_job_func;
 
+static volatile gboolean threadpool_shutdown;
+static volatile gboolean thread_finished;
+
 enum {
        STATE_WAITING,
        STATE_IN_PROGRESS,
@@ -109,7 +101,7 @@ thread_func (void *thread_data)
                gboolean do_idle = continue_idle_job ();
                SgenThreadPoolJob *job = get_job_and_set_in_progress ();
 
-               if (!job && !do_idle) {
+               if (!job && !do_idle && !threadpool_shutdown) {
                        /*
                         * pthread_cond_wait() can return successfully despite the condition
                         * not being signalled, so we have to run this in a loop until we
@@ -134,8 +126,7 @@ thread_func (void *thread_data)
                         * have to broadcast.
                         */
                        mono_os_cond_signal (&done_cond);
-               } else {
-                       SGEN_ASSERT (0, do_idle, "Why did we unlock if we still have to wait for idle?");
+               } else if (do_idle) {
                        SGEN_ASSERT (0, idle_job_func, "Why do we have idle work when there's no idle job function?");
                        do {
                                idle_job_func (thread_data);
@@ -146,6 +137,13 @@ thread_func (void *thread_data)
 
                        if (!do_idle)
                                mono_os_cond_signal (&done_cond);
+               } else {
+                       SGEN_ASSERT (0, threadpool_shutdown, "Why did we unlock if no jobs and not shutting down?");
+                       mono_os_mutex_lock (&lock);
+                       thread_finished = TRUE;
+                       mono_os_cond_signal (&done_cond);
+                       mono_os_mutex_unlock (&lock);
+                       return 0;
                }
        }
 
@@ -168,6 +166,24 @@ sgen_thread_pool_init (int num_threads, SgenThreadPoolThreadInitFunc init_func,
        mono_native_thread_create (&thread, thread_func, thread_datas ? thread_datas [0] : NULL);
 }
 
+void
+sgen_thread_pool_shutdown (void)
+{
+       if (!thread)
+               return;
+
+       mono_os_mutex_lock (&lock);
+       threadpool_shutdown = TRUE;
+       mono_os_cond_signal (&work_cond);
+       while (!thread_finished)
+               mono_os_cond_wait (&done_cond, &lock);
+       mono_os_mutex_unlock (&lock);
+
+       mono_os_mutex_destroy (&lock);
+       mono_os_cond_destroy (&work_cond);
+       mono_os_cond_destroy (&done_cond);
+}
+
 SgenThreadPoolJob*
 sgen_thread_pool_job_alloc (const char *name, SgenThreadPoolJobFunc func, size_t size)
 {
index 4dcb3a9a14b76195c06f3ccaf396cdf67dd1e9df..339526ca59876dac1ca4422a818e67421d68ee47 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGEN_THREAD_POOL_H__
@@ -37,6 +26,8 @@ typedef gboolean (*SgenThreadPoolContinueIdleJobFunc) (void);
 
 void sgen_thread_pool_init (int num_threads, SgenThreadPoolThreadInitFunc init_func, SgenThreadPoolIdleJobFunc idle_func, SgenThreadPoolContinueIdleJobFunc continue_idle_func, void **thread_datas);
 
+void sgen_thread_pool_shutdown (void);
+
 SgenThreadPoolJob* sgen_thread_pool_job_alloc (const char *name, SgenThreadPoolJobFunc func, size_t size);
 /* This only needs to be called on jobs that are not enqueued. */
 void sgen_thread_pool_job_free (SgenThreadPoolJob *job);
index f1212c658c4c755954fba3d3927e62742cfe836e..adc600a090f3dc801f8d1b16b4796acb28a69988 100644 (file)
@@ -5,18 +5,7 @@
  * Copyright 2003-2010 Novell, Inc.
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -64,6 +53,7 @@ typedef gint32 State;
 static volatile State workers_state;
 
 static SgenObjectOperations * volatile idle_func_object_ops;
+static SgenThreadPoolJob * volatile preclean_job;
 
 static guint64 stat_workers_num_finished;
 
@@ -230,7 +220,13 @@ marker_idle_func (void *data_untyped)
 
                sgen_drain_gray_stack (ctx);
        } else {
-               worker_try_finish ();
+               SgenThreadPoolJob *job = preclean_job;
+               if (job) {
+                       sgen_thread_pool_job_enqueue (job);
+                       preclean_job = NULL;
+               } else {
+                       worker_try_finish ();
+               }
        }
 }
 
@@ -287,6 +283,8 @@ sgen_workers_init (int num_workers)
 void
 sgen_workers_stop_all_workers (void)
 {
+       preclean_job = NULL;
+       mono_memory_write_barrier ();
        forced_stop = TRUE;
 
        sgen_thread_pool_wait_for_all_jobs ();
@@ -295,10 +293,11 @@ sgen_workers_stop_all_workers (void)
 }
 
 void
-sgen_workers_start_all_workers (SgenObjectOperations *object_ops)
+sgen_workers_start_all_workers (SgenObjectOperations *object_ops, SgenThreadPoolJob *job)
 {
        forced_stop = FALSE;
        idle_func_object_ops = object_ops;
+       preclean_job = job;
        mono_memory_write_barrier ();
 
        sgen_workers_ensure_awake ();
index 4a3703555ff19613ee1dcc291361ef0c356566ca..780d2eb6df921ed6a096879c4876eef75f8adbaf 100644 (file)
@@ -4,18 +4,7 @@
  * Copyright 2011 Xamarin Inc (http://www.xamarin.com)
  * Copyright (C) 2012 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SGEN_WORKER_H__
@@ -30,7 +19,7 @@ struct _WorkerData {
 
 void sgen_workers_init (int num_workers);
 void sgen_workers_stop_all_workers (void);
-void sgen_workers_start_all_workers (SgenObjectOperations *object_ops);
+void sgen_workers_start_all_workers (SgenObjectOperations *object_ops, SgenThreadPoolJob *finish_job);
 void sgen_workers_ensure_awake (void);
 void sgen_workers_init_distribute_gray_queue (void);
 void sgen_workers_enqueue_job (SgenThreadPoolJob *job, gboolean enqueue);
index b410d785f993dba01dbc6b3d765ed64d069dad0e..86a740ca0579e5dc75f60f5025acf3b457ca0959 100644 (file)
@@ -435,7 +435,8 @@ BASE_TEST_CS_SRC=           \
        pinvoke_ppcs.cs \
        pinvoke_ppci.cs \
        pinvoke_ppcf.cs \
-       pinvoke_ppcd.cs
+       pinvoke_ppcd.cs \
+       bug-29585.cs
 
 TEST_CS_SRC_DIST=      \
        $(BASE_TEST_CS_SRC)     \
@@ -709,7 +710,7 @@ EXTRA_DIST=test-driver test-runner.cs $(TEST_CS_SRC_DIST) $(TEST_IL_SRC) \
        $(ILASM) -out:$@ $<
 
 %.exe: %.cs TestDriver.dll
-       $(MCS) -r:System.dll -r:System.Xml.dll -r:System.Core.dll -r:TestDriver.dll -out:$@ $<
+       $(MCS) -r:System.dll -r:System.Xml.dll -r:System.Core.dll -r:TestDriver.dll -r:Mono.Posix.dll -out:$@ $<
 
 # mkbundle works on ppc, but the pkg-config POC doesn't when run with make test
 if POWERPC
@@ -877,7 +878,7 @@ runtest: $(TESTSI_CS) $(TESTSI_IL) $(TESTBS) libtest.la $(PREREQSI_IL) $(PREREQS
 
 runtest-managed: test-runner.exe $(TESTSI_CS) $(TESTSI_IL) $(TESTBS) libtest.la $(PREREQSI_IL) $(PREREQSI_CS)
        @if [ "x$$CI" = "x1" ]; then disabled_tests="$(DISABLED_TESTS_WRENCH)"; else disabled_tests="$(DISABLED_TESTS)"; fi; \
-       $(RUNTIME) --debug ./test-runner.exe -j a --testsuite-name "runtime" --disabled "$${disabled_tests}" $(TESTSI_CS) $(TESTBS) $(TESTSI_IL)
+       $(RUNTIME) --debug ./test-runner.exe -j a --testsuite-name "runtime" --timeout 300 --disabled "$${disabled_tests}" $(TESTSI_CS) $(TESTBS) $(TESTSI_IL)
 
 runtest-managed-serial: test-runner.exe $(TESTSI_CS) $(TESTSI_IL) $(TESTBS) libtest.la $(PREREQSI_IL) $(PREREQSI_CS)
        @if [ "x$$CI" = "x1" ]; then disabled_tests="$(DISABLED_TESTS_WRENCH)"; else disabled_tests="$(DISABLED_TESTS)"; fi; \
@@ -963,7 +964,7 @@ debug-casts:
        @$(MCS) -r:TestDriver.dll $(srcdir)/debug-casts.cs
        @$(RUNTIME) --debug=casts debug-casts.exe
 
-EXTRA_DIST += sgen-bridge.cs sgen-descriptors.cs sgen-gshared-vtype.cs sgen-bridge-major-fragmentation.cs sgen-domain-unload.cs sgen-weakref-stress.cs sgen-cementing-stress.cs sgen-case-23400.cs     finalizer-wait.cs critical-finalizers.cs sgen-domain-unload-2.cs sgen-suspend.cs sgen-new-threads-dont-join-stw.cs sgen-bridge-xref.cs bug-17590.cs sgen-toggleref.cs
+EXTRA_DIST += sgen-bridge.cs sgen-descriptors.cs sgen-gshared-vtype.cs sgen-bridge-major-fragmentation.cs sgen-domain-unload.cs sgen-weakref-stress.cs sgen-cementing-stress.cs sgen-case-23400.cs     finalizer-wait.cs critical-finalizers.cs sgen-domain-unload-2.cs sgen-suspend.cs sgen-new-threads-dont-join-stw.cs sgen-bridge-xref.cs bug-17590.cs sgen-toggleref.cs sgen-bridge-gchandle.cs
 
 
 sgen-tests:
@@ -1104,6 +1105,38 @@ sgen-bridge2-tests-plain-tarjan-bridge: $(SGEN_BRIDGE2_TESTS) test-runner.exe
 sgen-bridge2-tests-ms-split-tarjan-bridge: $(SGEN_BRIDGE2_TESTS) test-runner.exe
        MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=2Bridge" MONO_GC_PARAMS="bridge-implementation=tarjan,minor=split" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE2_TESTS)
 
+
+SGEN_BRIDGE3_TESTS=    \
+       sgen-bridge-gchandle.exe
+
+sgen-bridge3-tests: $(SGEN_BRIDGE3_TESTS)
+       $(MAKE) sgen-bridge3-tests-plain
+       $(MAKE) sgen-bridge3-tests-ms-conc
+       $(MAKE) sgen-bridge3-tests-ms-split
+       $(MAKE) sgen-bridge3-tests-plain-new-bridge
+       $(MAKE) sgen-bridge3-tests-ms-conc-new-bridge
+       $(MAKE) sgen-bridge3-tests-ms-split-new-bridge
+       $(MAKE) sgen-bridge3-tests-plain-tarjan-bridge
+       $(MAKE) sgen-bridge3-tests-ms-split-tarjan-bridge
+
+sgen-bridge3-tests-plain: $(SGEN_bridge3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-ms-conc: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="major=marksweep-conc" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-ms-split: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="minor=split" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-plain-new-bridge: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="bridge-implementation=new" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-ms-conc-new-bridge: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="bridge-implementation=new,major=marksweep-conc" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-ms-split-new-bridge: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="bridge-implementation=new,minor=split" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-plain-tarjan-bridge: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="bridge-implementation=tarjan" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+sgen-bridge3-tests-ms-split-tarjan-bridge: $(SGEN_BRIDGE3_TESTS) test-runner.exe
+       MONO_ENV_OPTIONS="--gc=sgen" MONO_GC_DEBUG="bridge=3Bridge" MONO_GC_PARAMS="bridge-implementation=tarjan,minor=split" $(RUNTIME) ./test-runner.exe --testsuite-name $@ --timeout 900 $(SGEN_BRIDGE3_TESTS)
+
+
 AOT_CONFIGURATIONS=    \
        "|regular"      \
        "--gc=boehm|boehm"
index c811eec33676834d4ce737fd0434385a9ce6987e..d4673c79584328524e8f56222d4ed9d2f51597ab 100644 (file)
@@ -98,7 +98,10 @@ class CrossDomainTester : MarshalByRefObject
 public class Tests
 {
        public static int Main(string[] args) {
-               return TestDriver.RunTests (typeof (Tests), args);
+               if (args.Length == 0)
+                       return TestDriver.RunTests (typeof (Tests), new String[] { "-v" });
+               else
+                       return TestDriver.RunTests (typeof (Tests), args);
        }
 
        public static int test_0_unload () {
diff --git a/mono/tests/bug-29585.cs b/mono/tests/bug-29585.cs
new file mode 100644 (file)
index 0000000..a1289fa
--- /dev/null
@@ -0,0 +1,54 @@
+namespace TestCase
+{
+    using System;
+    using System.Linq;
+    using System.Reflection;
+
+
+    public class MainClass
+    {
+        public static int Main()
+        {
+            return new GenericDerived<Param>().FindMethod();
+        }
+    }
+
+
+    interface Param
+    {
+    }
+
+
+    class GenericDerived<T> :
+        Abstract<GenericDerived<T>>
+    {
+        public int FindMethod()
+        {
+            return FindGenericMethod<T>();
+        }
+    }
+
+
+    abstract class Abstract<TDerived>
+        where TDerived : Abstract<TDerived>
+    {
+        protected virtual int FindGenericMethod<T>()
+        {
+            var method = typeof(TDerived)
+                .GetMethods(BindingFlags.Instance | BindingFlags.NonPublic)
+                .FirstOrDefault(x => x.Name == "FindGenericMethod" && x.IsGenericMethod);
+
+            Console.WriteLine("TDerived = {0}", typeof(TDerived));
+            Console.WriteLine("method = {0}", method);
+            Console.WriteLine("method.DeclaringType = {0}", method.DeclaringType);
+            Console.WriteLine("method.IsGenericMethod = {0}", method.IsGenericMethod);
+            Console.WriteLine("method.IsGenericMethodDefinition = {0}", method.IsGenericMethodDefinition);
+                       
+                       if (!method.IsGenericMethod)
+                               return 1;
+                       if (!method.IsGenericMethodDefinition)
+                               return 2;
+                       return 0;
+        }
+    }
+}
\ No newline at end of file
index c0d094fc56f1f2a262d9a42d77ccf0e67c01fff2..dbd2e9ad1cc108d8ee2ebbb383738f9b84999af4 100644 (file)
@@ -1117,6 +1117,14 @@ mono_test_marshal_virtual_delegate (VirtualDelegate del)
        return del (42);
 }
 
+typedef char* (STDCALL *IcallDelegate) (const char *);
+LIBTEST_API int STDCALL
+mono_test_marshal_icall_delegate (IcallDelegate del)
+{
+       char *res = del ("ABC");
+       return strcmp (res, "ABC") == 0 ? 0 : 1;
+}
+
 LIBTEST_API int STDCALL  
 mono_test_marshal_stringbuilder (char *s, int n)
 {
index cf87dbd103ebb573474156857868bb06f1522177..5e0f474ec40ac451ce6034bf5af400896980c0ca 100644 (file)
@@ -1,5 +1,6 @@
 //
 // Copyright 2011 Xamarin Inc (http://www.xamarin.com).
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
index 376e2000187f834b4b5ce0516fa1249cb5ced8cb..29ed8ea7eee8498f00e11aaf06d54b7109a8150d 100644 (file)
@@ -194,6 +194,11 @@ public class Tests {
        [DllImport ("libtest", EntryPoint="mono_test_marshal_virtual_delegate")]
        public static extern int mono_test_marshal_virtual_delegate (VirtualDelegate del);
 
+       [DllImport ("libtest", EntryPoint="mono_test_marshal_icall_delegate")]
+       public static extern int mono_test_marshal_icall_delegate (IcallDelegate del);
+
+       public delegate string IcallDelegate (IntPtr p);
+
        public delegate int TestDelegate (int a, ref SimpleStruct ss, int b);
 
        public delegate SimpleStruct SimpleDelegate2 (SimpleStruct ss);
@@ -1161,4 +1166,10 @@ public class Tests {
 
                return mono_test_marshal_virtual_delegate (b.get_del ());
        }
+
+       public static int test_0_icall_delegate () {
+               var m = typeof (Marshal).GetMethod ("PtrToStringAnsi", new Type[] { typeof (IntPtr) });
+
+               return mono_test_marshal_icall_delegate ((IcallDelegate)Delegate.CreateDelegate (typeof (IcallDelegate), m));
+       }
 }
index 9690179180636dd693a25f4074ec459840ddb700..da90ba1c35f5cc620149a389272f22af4539ba22 100644 (file)
@@ -10,7 +10,7 @@
 //
 // Bill Seurer (seurer@linux.vnet.ibm.com)
 //
-// (C) {Copyright holder}
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
index c4bafea09894ac1d0307a71e98fbea37d50950d9..602706345e91e17d3e953e19f9ca8a3fa1ff84da 100644 (file)
@@ -10,7 +10,7 @@
 //
 // Bill Seurer (seurer@linux.vnet.ibm.com)
 //
-// (C) {Copyright holder}
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
index a529a5331fecfb0ab0f98ad8ecfe4cfcd4ed341e..a7f519e557cef0ab9011a5487120becb5a64aba2 100644 (file)
@@ -10,7 +10,7 @@
 //
 // Bill Seurer (seurer@linux.vnet.ibm.com)
 //
-// (C) {Copyright holder}
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
index e7c1d395c79faf5ee446565b20609261e8b41ea6..34021e0b053a6c99d9728913c67563c442ba996c 100644 (file)
@@ -10,7 +10,7 @@
 //
 // Bill Seurer (seurer@linux.vnet.ibm.com)
 //
-// (C) {Copyright holder}
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
index a57a909850083ded55c984f0db75b7650915a952..08ad1d6eccd40994ab972de400b48d6f8d0b5d10 100644 (file)
@@ -10,7 +10,7 @@
 //
 // Bill Seurer (seurer@linux.vnet.ibm.com)
 //
-// (C) {Copyright holder}
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 
 using System;
diff --git a/mono/tests/sgen-bridge-gchandle.cs b/mono/tests/sgen-bridge-gchandle.cs
new file mode 100644 (file)
index 0000000..c9a7064
--- /dev/null
@@ -0,0 +1,78 @@
+using System;
+using System.Collections;
+using System.Threading;
+using System.Runtime.InteropServices;
+
+
+public class Bridge {
+       public int __test;
+       public string id;
+       
+       ~Bridge () {
+               try {Console.WriteLine ("bridge {0} gone", id);} catch (Exception) {}
+       }
+}
+
+
+/*
+Test scenario:
+       Alloc a bridge and create a gc handle to it
+       Get it collected.
+       Create another one and see it steal the handle of the previous one.
+
+
+*/
+class Driver {
+       public static GCHandle weak_track_handle;
+       public static GCHandle weak_track_handle2;
+
+       static void CreateFirstBridge () {
+               Bridge b = new Bridge() {
+                       __test = 0,
+                       id = "first",
+               };
+               weak_track_handle = GCHandle.Alloc (b, GCHandleType.WeakTrackResurrection);
+       }
+
+       static void CreateSecondBridge () {
+               Bridge b = new Bridge() {
+                       __test = 1,
+                       id = "second",
+               };
+               weak_track_handle2 = GCHandle.Alloc (b, GCHandleType.WeakTrackResurrection);
+       }
+
+       static void DumpHandle (GCHandle h, string name) {
+               Console.WriteLine ("{0}:{1:X} alloc:{2} hasValue:{2}", name, (IntPtr)h, h.IsAllocated, h.Target == null);
+       }
+
+       static int Main () {
+               var t = new Thread (CreateFirstBridge);
+               t.Start ();
+               t.Join ();
+
+               GC.Collect ();
+               GC.WaitForPendingFinalizers ();
+               Console.WriteLine ("GC DONE");
+
+               DumpHandle (weak_track_handle, "weak-track1");
+
+               t = new Thread (CreateSecondBridge);
+               t.Start ();
+               t.Join ();
+
+               GC.Collect ();
+               GC.WaitForPendingFinalizers ();
+               Console.WriteLine ("GC DONE");
+               DumpHandle (weak_track_handle, "weak-track1");
+               DumpHandle (weak_track_handle2, "weak-track2");
+               Console.WriteLine ("DONE");
+
+               if ((IntPtr)weak_track_handle == (IntPtr)weak_track_handle2) {
+                       Console.WriteLine ("FIRST HANDLE GOT DEALLOCATED!");
+                       return 1;
+               }
+
+               return 0;
+       }
+}
index d604294fee0884166128bd9687335ba1cd394e03..f4f2df11555816c07308e4935012b020ea486dd1 100644 (file)
@@ -3,6 +3,7 @@ using System.Collections;
 using System.Collections.Generic;
 using System.Threading;
 using System.Runtime.InteropServices;
+using System.Runtime.CompilerServices;
 
 public class Toggleref {
        public int __test;
@@ -42,23 +43,23 @@ class Driver {
                mono_gc_toggleref_add (Helper.ObjToPtr (obj), true);
        }
 
+       static Toggleref a, b;
+
        static void SetupLinks () {
-               var a = new Toggleref () { id = "root" };
-               var b = new Toggleref () { id = "child" };
-               a.link.Add (b);
-               a.__test = Toggleref.STRONG;
-               b.__test = Toggleref.WEAK;
-               Register (a);
-               Register (b);
-               root = new WeakReference<Toggleref> (a, false);
-               child = new WeakReference<Toggleref> (b, false);
+               var r = new Toggleref () { id = "root" };
+               var c = new Toggleref () { id = "child" };
+               r.link.Add (c);
+               r.__test = Toggleref.STRONG;
+               c.__test = Toggleref.WEAK;
+               Register (r);
+               Register (c);
+               root = new WeakReference<Toggleref> (r, false);
+               child = new WeakReference<Toggleref> (c, false);
        }
 
-       static Toggleref a, b;
-
-       static int Main ()
+       static int test_0_root_keeps_child ()
        {
-               
+               Console.WriteLine ("test_0_root_keeps_child");
                var t = new Thread (SetupLinks);
                t.Start ();
                t.Join ();
@@ -94,6 +95,116 @@ class Driver {
 
 
                return 0;
+       }
+
+       static void SetupLinks2 () {
+               var r = new Toggleref () { id = "root" };
+               var c = new Toggleref () { id = "child" };
+
+               r.__test = Toggleref.STRONG;
+               c.__test = Toggleref.WEAK;
+               Register (r);
+               Register (c);
+               root = new WeakReference<Toggleref> (r, false);
+               child = new WeakReference<Toggleref> (c, false);
+       }
+
+       static int test_0_child_goes_away ()
+       {
+               Console.WriteLine ("test_0_child_goes_away");
+
+               var t = new Thread (SetupLinks2);
+               t.Start ();
+               t.Join ();
+
+               GC.Collect ();
+               GC.WaitForPendingFinalizers ();
+
+               Console.WriteLine ("try get A {0}", root.TryGetTarget (out a));
+               Console.WriteLine ("try get B {0}", child.TryGetTarget (out b));
+               Console.WriteLine ("a is null {0}", a == null);
+               Console.WriteLine ("b is null {0}", b == null);
+               if (a == null || b != null)
+                       return 1;
+               Console.WriteLine ("a test {0}", a.__test);
+
+               return 0;
+       }
+
+       static ConditionalWeakTable<Toggleref, object> cwt = new ConditionalWeakTable<Toggleref, object> ();
+       static WeakReference<object> root_value, child_value;
+       static object a_val, b_val;
+
+
+       static void SetupLinks3 () {
+               var r = new Toggleref () { id = "root" };
+               var c = new Toggleref () { id = "child" };
+
+               r.__test = Toggleref.STRONG;
+               c.__test = Toggleref.WEAK;
+               Register (r);
+               Register (c);
+               root = new WeakReference<Toggleref> (r, false);
+               child = new WeakReference<Toggleref> (c, false);
+
+               var root_val = new object ();
+               var child_val = new object ();
+
+               cwt.Add (r, root_val);
+               cwt.Add (c, child_val);
+
+               root_value = new WeakReference<object> (root_val, false);
+               child_value = new WeakReference<object> (child_val, false);
+       }
+
+       static int test_0_CWT_keep_child_alive ()
+       {
+               Console.WriteLine ("test_0_CWT_keep_child_alive");
+
+               var t = new Thread (SetupLinks3);
+               t.Start ();
+               t.Join ();
+
+               GC.Collect ();
+               GC.WaitForPendingFinalizers ();
+
+               Console.WriteLine ("try get A {0}", root.TryGetTarget (out a));
+               Console.WriteLine ("try get B {0}", child.TryGetTarget (out b));
+               Console.WriteLine ("a is null {0}", a == null);
+               Console.WriteLine ("b is null {0}", b == null);
+               if (a == null || b != null)
+                       return 1;
+               Console.WriteLine ("a test {0}", a.__test);
+
+               Console.WriteLine ("try get a_val {0}", root_value.TryGetTarget (out a_val));
+               Console.WriteLine ("try get v_val {0}", child_value.TryGetTarget (out b_val));
+
+               //the strong toggleref must keep the CWT value to remains alive
+               if (a_val == null)
+                       return 2;
+
+               //the weak toggleref should allow the CWT value to go away
+               if (b_val != null)
+                       return 3;
+
+               object res_value = null;
+               bool res = cwt.TryGetValue (a, out res_value);
+               Console.WriteLine ("CWT result {0} -> {1}", res, res_value == a_val);
+
+               //the strong val is not on the CWT
+               if (!res)
+                       return 4;
+
+               //for some reason the value is not the right one
+               if (res_value != a_val)
+                       return 5;
+
+               return 0;
+       }
 
+       static int Main (string[] args)
+       {
+               return TestDriver.RunTests (typeof (Driver), args);
        }
+
 }
\ No newline at end of file
index e58e009a269117778ad7472a5b7f780a33221539..95011edf2c9c2d6d200ad577696870a5813372f0 100644 (file)
@@ -6,24 +6,7 @@
 //
 // Copyright (C) 2008 Novell, Inc (http://www.novell.com)
 //
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 //
 using System;
 using System.IO;
@@ -33,6 +16,7 @@ using System.Collections.Generic;
 using System.Globalization;
 using System.Xml;
 using System.Text.RegularExpressions;
+using Mono.Unix.Native;
 
 //
 // This is a simple test runner with support for parallel execution
@@ -268,9 +252,19 @@ public class TestRunner
                                                        timedout.Add (data);
                                                }
 
+                                               // Force the process to print a thread dump
+                                               try {
+                                                       Syscall.kill (p.Id, Signum.SIGQUIT);
+                                                       Thread.Sleep (1000);
+                                               } catch {
+                                               }
+
                                                output.Write ("timed out");
 
-                                               p.Kill ();
+                                               try {
+                                                       p.Kill ();
+                                               } catch {
+                                               }
                                        } else if (p.ExitCode != expectedExitCode) {
                                                var end = DateTime.UtcNow;
 
index e66f751d24e4033bc08aaa520ee31862174679ca..b4627e0d048c8d3dc1499e8365b2effd501db705 100644 (file)
@@ -6,24 +6,7 @@
 //
 // Copyright (C) 2007 Novell, Inc (http://www.novell.com)
 //
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.//
 //
 using System;
 using System.IO;
index 2233f10ce72855e2414605204bad7efe64d9949e..cb18ef67a89ea12c3a8b952ad65598455a8ee7d9 100644 (file)
@@ -6,25 +6,7 @@
 //
 // Copyright (C) 2008 Novell, Inc (http://www.novell.com)
 //
-// Permission is hereby granted, free of charge, to any person obtaining
-// a copy of this software and associated documentation files (the
-// "Software"), to deal in the Software without restriction, including
-// without limitation the rights to use, copy, modify, merge, publish,
-// distribute, sublicense, and/or sell copies of the Software, and to
-// permit persons to whom the Software is furnished to do so, subject to
-// the following conditions:
-// 
-// The above copyright notice and this permission notice shall be
-// included in all copies or substantial portions of the Software.
-// 
-// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
-// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
-// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
-// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
-// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
-//
+// Licensed under the MIT license. See LICENSE file in the project root for full license information.
 using System;
 using System.IO;
 using System.Reflection;
diff --git a/mono/tests/verifier/COPYING.LIB b/mono/tests/verifier/COPYING.LIB
deleted file mode 100755 (executable)
index a14a130..0000000
+++ /dev/null
@@ -1,484 +0,0 @@
-These CLI bytecode verifier tests are licensed under the 
-terms of the GNU Library General Public License, version 2.
-                 
-               GNU LIBRARY GENERAL PUBLIC LICENSE
-                      Version 2, June 1991
-
- Copyright (C) 1991 Free Software Foundation, Inc.
-                    675 Mass Ave, Cambridge, MA 02139, USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
-[This is the first released version of the library GPL.  It is
- numbered 2 because it goes with version 2 of the ordinary GPL.]
-
-                           Preamble
-
-  The licenses for most software are designed to take away your
-freedom to share and change it.  By contrast, the GNU General Public
-Licenses are intended to guarantee your freedom to share and change
-free software--to make sure the software is free for all its users.
-
-  This license, the Library General Public License, applies to some
-specially designated Free Software Foundation software, and to any
-other libraries whose authors decide to use it.  You can use it for
-your libraries, too.
-
-  When we speak of free software, we are referring to freedom, not
-price.  Our General Public Licenses are designed to make sure that you
-have the freedom to distribute copies of free software (and charge for
-this service if you wish), that you receive source code or can get it
-if you want it, that you can change the software or use pieces of it
-in new free programs; and that you know you can do these things.
-
-  To protect your rights, we need to make restrictions that forbid
-anyone to deny you these rights or to ask you to surrender the rights.
-These restrictions translate to certain responsibilities for you if
-you distribute copies of the library, or if you modify it.
-
-  For example, if you distribute copies of the library, whether gratis
-or for a fee, you must give the recipients all the rights that we gave
-you.  You must make sure that they, too, receive or can get the source
-code.  If you link a program with the library, you must provide
-complete object files to the recipients so that they can relink them
-with the library, after making changes to the library and recompiling
-it.  And you must show them these terms so they know their rights.
-
-  Our method of protecting your rights has two steps: (1) copyright
-the library, and (2) offer you this license which gives you legal
-permission to copy, distribute and/or modify the library.
-
-  Also, for each distributor's protection, we want to make certain
-that everyone understands that there is no warranty for this free
-library.  If the library is modified by someone else and passed on, we
-want its recipients to know that what they have is not the original
-version, so that any problems introduced by others will not reflect on
-the original authors' reputations.
-\f
-  Finally, any free program is threatened constantly by software
-patents.  We wish to avoid the danger that companies distributing free
-software will individually obtain patent licenses, thus in effect
-transforming the program into proprietary software.  To prevent this,
-we have made it clear that any patent must be licensed for everyone's
-free use or not licensed at all.
-
-  Most GNU software, including some libraries, is covered by the ordinary
-GNU General Public License, which was designed for utility programs.  This
-license, the GNU Library General Public License, applies to certain
-designated libraries.  This license is quite different from the ordinary
-one; be sure to read it in full, and don't assume that anything in it is
-the same as in the ordinary license.
-
-  The reason we have a separate public license for some libraries is that
-they blur the distinction we usually make between modifying or adding to a
-program and simply using it.  Linking a program with a library, without
-changing the library, is in some sense simply using the library, and is
-analogous to running a utility program or application program.  However, in
-a textual and legal sense, the linked executable is a combined work, a
-derivative of the original library, and the ordinary General Public License
-treats it as such.
-
-  Because of this blurred distinction, using the ordinary General
-Public License for libraries did not effectively promote software
-sharing, because most developers did not use the libraries.  We
-concluded that weaker conditions might promote sharing better.
-
-  However, unrestricted linking of non-free programs would deprive the
-users of those programs of all benefit from the free status of the
-libraries themselves.  This Library General Public License is intended to
-permit developers of non-free programs to use free libraries, while
-preserving your freedom as a user of such programs to change the free
-libraries that are incorporated in them.  (We have not seen how to achieve
-this as regards changes in header files, but we have achieved it as regards
-changes in the actual functions of the Library.)  The hope is that this
-will lead to faster development of free libraries.
-
-  The precise terms and conditions for copying, distribution and
-modification follow.  Pay close attention to the difference between a
-"work based on the library" and a "work that uses the library".  The
-former contains code derived from the library, while the latter only
-works together with the library.
-
-  Note that it is possible for a library to be covered by the ordinary
-General Public License rather than by this special one.
-\f
-                 GNU LIBRARY GENERAL PUBLIC LICENSE
-   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
-  0. This License Agreement applies to any software library which
-contains a notice placed by the copyright holder or other authorized
-party saying it may be distributed under the terms of this Library
-General Public License (also called "this License").  Each licensee is
-addressed as "you".
-
-  A "library" means a collection of software functions and/or data
-prepared so as to be conveniently linked with application programs
-(which use some of those functions and data) to form executables.
-
-  The "Library", below, refers to any such software library or work
-which has been distributed under these terms.  A "work based on the
-Library" means either the Library or any derivative work under
-copyright law: that is to say, a work containing the Library or a
-portion of it, either verbatim or with modifications and/or translated
-straightforwardly into another language.  (Hereinafter, translation is
-included without limitation in the term "modification".)
-
-  "Source code" for a work means the preferred form of the work for
-making modifications to it.  For a library, complete source code means
-all the source code for all modules it contains, plus any associated
-interface definition files, plus the scripts used to control compilation
-and installation of the library.
-
-  Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope.  The act of
-running a program using the Library is not restricted, and output from
-such a program is covered only if its contents constitute a work based
-on the Library (independent of the use of the Library in a tool for
-writing it).  Whether that is true depends on what the Library does
-and what the program that uses the Library does.
-  
-  1. You may copy and distribute verbatim copies of the Library's
-complete source code as you receive it, in any medium, provided that
-you conspicuously and appropriately publish on each copy an
-appropriate copyright notice and disclaimer of warranty; keep intact
-all the notices that refer to this License and to the absence of any
-warranty; and distribute a copy of this License along with the
-Library.
-
-  You may charge a fee for the physical act of transferring a copy,
-and you may at your option offer warranty protection in exchange for a
-fee.
-\f
-  2. You may modify your copy or copies of the Library or any portion
-of it, thus forming a work based on the Library, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
-    a) The modified work must itself be a software library.
-
-    b) You must cause the files modified to carry prominent notices
-    stating that you changed the files and the date of any change.
-
-    c) You must cause the whole of the work to be licensed at no
-    charge to all third parties under the terms of this License.
-
-    d) If a facility in the modified Library refers to a function or a
-    table of data to be supplied by an application program that uses
-    the facility, other than as an argument passed when the facility
-    is invoked, then you must make a good faith effort to ensure that,
-    in the event an application does not supply such function or
-    table, the facility still operates, and performs whatever part of
-    its purpose remains meaningful.
-
-    (For example, a function in a library to compute square roots has
-    a purpose that is entirely well-defined independent of the
-    application.  Therefore, Subsection 2d requires that any
-    application-supplied function or table used by this function must
-    be optional: if the application does not supply it, the square
-    root function must still compute square roots.)
-
-These requirements apply to the modified work as a whole.  If
-identifiable sections of that work are not derived from the Library,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works.  But when you
-distribute the same sections as part of a whole which is a work based
-on the Library, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote
-it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Library.
-
-In addition, mere aggregation of another work not based on the Library
-with the Library (or with a work based on the Library) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
-  3. You may opt to apply the terms of the ordinary GNU General Public
-License instead of this License to a given copy of the Library.  To do
-this, you must alter all the notices that refer to this License, so
-that they refer to the ordinary GNU General Public License, version 2,
-instead of to this License.  (If a newer version than version 2 of the
-ordinary GNU General Public License has appeared, then you can specify
-that version instead if you wish.)  Do not make any other change in
-these notices.
-\f
-  Once this change is made in a given copy, it is irreversible for
-that copy, so the ordinary GNU General Public License applies to all
-subsequent copies and derivative works made from that copy.
-
-  This option is useful when you wish to copy part of the code of
-the Library into a program that is not a library.
-
-  4. You may copy and distribute the Library (or a portion or
-derivative of it, under Section 2) in object code or executable form
-under the terms of Sections 1 and 2 above provided that you accompany
-it with the complete corresponding machine-readable source code, which
-must be distributed under the terms of Sections 1 and 2 above on a
-medium customarily used for software interchange.
-
-  If distribution of object code is made by offering access to copy
-from a designated place, then offering equivalent access to copy the
-source code from the same place satisfies the requirement to
-distribute the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
-  5. A program that contains no derivative of any portion of the
-Library, but is designed to work with the Library by being compiled or
-linked with it, is called a "work that uses the Library".  Such a
-work, in isolation, is not a derivative work of the Library, and
-therefore falls outside the scope of this License.
-
-  However, linking a "work that uses the Library" with the Library
-creates an executable that is a derivative of the Library (because it
-contains portions of the Library), rather than a "work that uses the
-library".  The executable is therefore covered by this License.
-Section 6 states terms for distribution of such executables.
-
-  When a "work that uses the Library" uses material from a header file
-that is part of the Library, the object code for the work may be a
-derivative work of the Library even though the source code is not.
-Whether this is true is especially significant if the work can be
-linked without the Library, or if the work is itself a library.  The
-threshold for this to be true is not precisely defined by law.
-
-  If such an object file uses only numerical parameters, data
-structure layouts and accessors, and small macros and small inline
-functions (ten lines or less in length), then the use of the object
-file is unrestricted, regardless of whether it is legally a derivative
-work.  (Executables containing this object code plus portions of the
-Library will still fall under Section 6.)
-
-  Otherwise, if the work is a derivative of the Library, you may
-distribute the object code for the work under the terms of Section 6.
-Any executables containing that work also fall under Section 6,
-whether or not they are linked directly with the Library itself.
-\f
-  6. As an exception to the Sections above, you may also compile or
-link a "work that uses the Library" with the Library to produce a
-work containing portions of the Library, and distribute that work
-under terms of your choice, provided that the terms permit
-modification of the work for the customer's own use and reverse
-engineering for debugging such modifications.
-
-  You must give prominent notice with each copy of the work that the
-Library is used in it and that the Library and its use are covered by
-this License.  You must supply a copy of this License.  If the work
-during execution displays copyright notices, you must include the
-copyright notice for the Library among them, as well as a reference
-directing the user to the copy of this License.  Also, you must do one
-of these things:
-
-    a) Accompany the work with the complete corresponding
-    machine-readable source code for the Library including whatever
-    changes were used in the work (which must be distributed under
-    Sections 1 and 2 above); and, if the work is an executable linked
-    with the Library, with the complete machine-readable "work that
-    uses the Library", as object code and/or source code, so that the
-    user can modify the Library and then relink to produce a modified
-    executable containing the modified Library.  (It is understood
-    that the user who changes the contents of definitions files in the
-    Library will not necessarily be able to recompile the application
-    to use the modified definitions.)
-
-    b) Accompany the work with a written offer, valid for at
-    least three years, to give the same user the materials
-    specified in Subsection 6a, above, for a charge no more
-    than the cost of performing this distribution.
-
-    c) If distribution of the work is made by offering access to copy
-    from a designated place, offer equivalent access to copy the above
-    specified materials from the same place.
-
-    d) Verify that the user has already received a copy of these
-    materials or that you have already sent this user a copy.
-
-  For an executable, the required form of the "work that uses the
-Library" must include any data and utility programs needed for
-reproducing the executable from it.  However, as a special exception,
-the source code distributed need not include anything that is normally
-distributed (in either source or binary form) with the major
-components (compiler, kernel, and so on) of the operating system on
-which the executable runs, unless that component itself accompanies
-the executable.
-
-  It may happen that this requirement contradicts the license
-restrictions of other proprietary libraries that do not normally
-accompany the operating system.  Such a contradiction means you cannot
-use both them and the Library together in an executable that you
-distribute.
-\f
-  7. You may place library facilities that are a work based on the
-Library side-by-side in a single library together with other library
-facilities not covered by this License, and distribute such a combined
-library, provided that the separate distribution of the work based on
-the Library and of the other library facilities is otherwise
-permitted, and provided that you do these two things:
-
-    a) Accompany the combined library with a copy of the same work
-    based on the Library, uncombined with any other library
-    facilities.  This must be distributed under the terms of the
-    Sections above.
-
-    b) Give prominent notice with the combined library of the fact
-    that part of it is a work based on the Library, and explaining
-    where to find the accompanying uncombined form of the same work.
-
-  8. You may not copy, modify, sublicense, link with, or distribute
-the Library except as expressly provided under this License.  Any
-attempt otherwise to copy, modify, sublicense, link with, or
-distribute the Library is void, and will automatically terminate your
-rights under this License.  However, parties who have received copies,
-or rights, from you under this License will not have their licenses
-terminated so long as such parties remain in full compliance.
-
-  9. You are not required to accept this License, since you have not
-signed it.  However, nothing else grants you permission to modify or
-distribute the Library or its derivative works.  These actions are
-prohibited by law if you do not accept this License.  Therefore, by
-modifying or distributing the Library (or any work based on the
-Library), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Library or works based on it.
-
-  10. Each time you redistribute the Library (or any work based on the
-Library), the recipient automatically receives a license from the
-original licensor to copy, distribute, link with or modify the Library
-subject to these terms and conditions.  You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties to
-this License.
-\f
-  11. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License.  If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Library at all.  For example, if a patent
-license would not permit royalty-free redistribution of the Library by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Library.
-
-If any portion of this section is held invalid or unenforceable under any
-particular circumstance, the balance of the section is intended to apply,
-and the section as a whole is intended to apply in other circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system which is
-implemented by public license practices.  Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
-  12. If the distribution and/or use of the Library is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Library under this License may add
-an explicit geographical distribution limitation excluding those countries,
-so that distribution is permitted only in or among countries not thus
-excluded.  In such case, this License incorporates the limitation as if
-written in the body of this License.
-
-  13. The Free Software Foundation may publish revised and/or new
-versions of the Library General Public License from time to time.
-Such new versions will be similar in spirit to the present version,
-but may differ in detail to address new problems or concerns.
-
-Each version is given a distinguishing version number.  If the Library
-specifies a version number of this License which applies to it and
-"any later version", you have the option of following the terms and
-conditions either of that version or of any later version published by
-the Free Software Foundation.  If the Library does not specify a
-license version number, you may choose any version ever published by
-the Free Software Foundation.
-\f
-  14. If you wish to incorporate parts of the Library into other free
-programs whose distribution conditions are incompatible with these,
-write to the author to ask for permission.  For software which is
-copyrighted by the Free Software Foundation, write to the Free
-Software Foundation; we sometimes make exceptions for this.  Our
-decision will be guided by the two goals of preserving the free status
-of all derivatives of our free software and of promoting the sharing
-and reuse of software generally.
-
-                           NO WARRANTY
-
-  15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO
-WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.
-EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR
-OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY
-KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE
-IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
-PURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE
-LIBRARY IS WITH YOU.  SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME
-THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.
-
-  16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN
-WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY
-AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU
-FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR
-CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE
-LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
-RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
-FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
-SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH
-DAMAGES.
-
-                    END OF TERMS AND CONDITIONS
-\f
-     Appendix: How to Apply These Terms to Your New Libraries
-
-  If you develop a new library, and you want it to be of the greatest
-possible use to the public, we recommend making it free software that
-everyone can redistribute and change.  You can do so by permitting
-redistribution under these terms (or, alternatively, under the terms of the
-ordinary General Public License).
-
-  To apply these terms, attach the following notices to the library.  It is
-safest to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least the
-"copyright" line and a pointer to where the full notice is found.
-
-    <one line to give the library's name and a brief idea of what it does.>
-    Copyright (C) <year>  <name of author>
-
-    This library is free software; you can redistribute it and/or
-    modify it under the terms of the GNU Library General Public
-    License as published by the Free Software Foundation; either
-    version 2 of the License, or (at your option) any later version.
-
-    This library 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
-    Library General Public License for more details.
-
-    You should have received a copy of the GNU Library General Public
-    License along with this library; if not, write to the Free
-    Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-
-Also add information on how to contact you by electronic and paper mail.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the library, if
-necessary.  Here is a sample; alter the names:
-
-  Yoyodyne, Inc., hereby disclaims all copyright interest in the
-  library `Frob' (a library for tweaking knobs) written by James Random Hacker.
-
-  <signature of Ty Coon>, 1 April 1990
-  Ty Coon, President of Vice
-
-That's all there is to it!
index c170df2714ec8499ac96e8391aaa2f1b8a583a01..b61302fec3a7ab135a8e1d1c19702d42ba60f44e 100644 (file)
@@ -1,19 +1,19 @@
 
 %.exe: %.cil
-       ilasm2 -out:$@ $<
+       ilasm -out:$@ $<
 
 BatchCompiler.exe: BatchCompiler.cs
-       gmcs -r:../../../mcs/class/lib/net_2_0/ilasm.exe BatchCompiler.cs
+       mcs -r:../../../mcs/class/lib/net_4_x/ilasm.exe BatchCompiler.cs
 
 test_lib.dll: test_lib.cs
-       gmcs test_lib.cs -target:library
+       mcs test_lib.cs -target:library
 
 compile-stamp: generate-stamp BatchCompiler.exe test_lib.dll
        for i in *.cs; do \
                EXE="`echo $$i | cut -d. -f1`.exe"; \
                DLL="`echo $$i | cut -d. -f1`.dll"; \
                if ! [ -f $$EXE ] && ! [ -f $$DLL ]; then \
-                       gmcs /unsafe $$i; \
+                       mcs /unsafe $$i; \
                fi \
        done 
        #MONO_PATH=../../../mcs/class/lib/net_2_0/ mono BatchCompiler.exe
@@ -42,7 +42,7 @@ run-test: compile-stamp
                then \
                        RES=3; \
                fi; \
-               if [ "$$FIRST" == "unverifiable" ] || [ "$FIRST" == "typeunverifiable" ]; \
+               if [ "$$FIRST" == "unverifiable" ] || [ "$$FIRST" == "typeunverifiable" ]; \
                then \
                        RES=2; \
                fi; \
@@ -56,37 +56,37 @@ run-test: compile-stamp
                fi; \
                if [ "$$FIRST" == "strict" ]; \
                then \
-                       #in strict more it must fail under strict check and pass under non-strict check \
+                       echo "#in strict more it must fail under strict check and pass under non-strict check" >/dev/null; \
                        ../../metadata/pedump --verify partial-md,error,warn,cls,code $$TEST.exe >/dev/null 2>/dev/null; \
                        R1=$$?; \
                        ../../metadata/pedump --verify partial-md,error,warn,cls,code,non-strict $$TEST.exe >/dev/null 2>/dev/null; \
                        R2=$$?; \
                        if [ $$R1 != 2 ] && [ $$R1 != 3 ]; then \
                                echo "$$TEST is strict but did not fail under strict check, got $${R1} but expected 2 or 3"; \
-                       fi \
-                       #non-strict result \
+                       fi; \
+                       echo "#non-strict result" >/dev/null; \
                        if [ $$R2 != 0 ]; then \
                                echo "$$TEST is strict but did not pass under non-strict check, got $${R2} but expected 0"; \
-                       fi \
+                       fi; \
                elif [ "$$FIRST" == "typeunverifiable" ]; then \
-                       #in type unverifiable more it must fail under verifiable mode but it's ok under valid mode \
+                       echo "#in type unverifiable more it must fail under verifiable mode but it's ok under valid mode" >/dev/null; \
                        ../../metadata/pedump --verify partial-md,error,warn,cls,code $$TEST.exe  >/dev/null 2>/dev/null; \
                        R1=$$?; \
                        ../../metadata/pedump --verify partial-md,error,warn,cls,code,valid-only $$TEST.exe  >/dev/null 2>/dev/null; \
                        R2=$$?; \
                        if [ $$R1 != 3 ]; then \
                                echo "$$TEST is type unverifiable but did not fail under verifiable check, got $${R1} but expected 3"; \
-                       fi \
-                       #type unverifiable result \
+                       fi; \
+                       echo "#type unverifiable result" >/dev/null; \
                        if [ $$R2 != 0 ]; then \
                                echo "$$TEST is type unverifiable but did not pass under non-strict check, got $${R2} but expected 0"; \
-                       fi \
+                       fi; \
                elif [ $$RES != 99 ]; then \
                        ../../metadata/pedump --verify partial-md,error,warn,cls,code $$TEST.exe >/dev/null 2>/dev/null; \
                        R=$$?; \
                        if [ $$R != $$RES ]; then \
                                echo "$$TEST failed expected $$RES but got $$R"; \
-                       fi \
+                       fi; \
                fi; \
        done
 
index bbbf83024848d1e285df2c10417a0125de7f4df8..72be8020ee54eb6d2d34905f68915604e0f0b700 100755 (executable)
@@ -13,7 +13,7 @@ TEST_MEMBER_ACCESS=$5
 TEST_EXTENDS=$6
 TEST_USE_SUB_CLASS=$7
 
-if [ "$TEST_EXTENDS" == "yes" ]; then
+if [ "$TEST_EXTENDS" = "yes" ]; then
        TEST_EXTENDS="extends Class"
        TEST_SUPER_TYPE="Class"
 else
@@ -21,7 +21,7 @@ else
        TEST_SUPER_TYPE="object"
 fi
 
-if [ "$TEST_USE_SUB_CLASS" == "yes" ]; then
+if [ "$TEST_USE_SUB_CLASS" = "yes" ]; then
        TEST_VAR_TYPE="ExampleClass"
 else
        TEST_VAR_TYPE="Class"
@@ -87,4 +87,4 @@ $SED -e "s/SUPER_TYPE/${TEST_SUPER_TYPE}/g" -e "s/VALIDITY/${TEST_VALIDITY}/g" -
                ret
        }
 }
-//EOF
\ No newline at end of file
+//EOF
index 73b79622f5b77461de8f3b3764aa7f87a692368e..4356497ea37651a6a257db532d0607c03b1017e5 100755 (executable)
@@ -11,7 +11,7 @@ TEST_BYTE_0=$3
 TEST_BYTE_1=$4
 
 
-if [ "$TEST_BYTE_1" == "" ] ; then
+if [ "x$TEST_BYTE_1" = "x" ] ; then
        TEST_BYTE_1="0";
 fi
 
index 5ebbbb99416c577541df95516d369ae1137f9e3c..019b453beb181e8a35fb69838eae9bca94dd06c3 100755 (executable)
@@ -12,7 +12,7 @@ TEST_TYPE2=$5
 TEST_INIT_EXP=$6
 TEST_INIT_VAL=$7
 
-if [ "$TEST_INIT_VAL" == "yes" ]; then
+if [ "$TEST_INIT_VAL" = "yes" ]; then
        TEST_INIT="$TEST_INIT_EXP\n\t\stloc.1"
 else
        TEST_INIT=""
@@ -50,4 +50,4 @@ $SED -e "s/INIT/${TEST_INIT}/g" -e "s/VALIDITY/${TEST_VALIDITY}/g" -e "s/TYPE1/$
        ldc.i4.0
        ret
 }
-//EOF
\ No newline at end of file
+//EOF
index 9522718a1c712f2e2d3417a8c7e756ca6a72c702..32428322b688a18ebd061db69c66814d75aa8634 100755 (executable)
@@ -11,7 +11,7 @@ TEST_OP=$3
 TEST_BEFORE_OP=$4
 TEST_CONSTRAINT_TYPE=$5
 
-if [ "$TEST_CONSTRAINT_TYPE" == "" ]; then
+if [ "x$TEST_CONSTRAINT_TYPE" = "x" ]; then
        TEST_CONSTRAINT_TYPE="IFace";
 fi
 
index 5ae54d3cafff22dcadeadfb4ba441fd7bc11e0e5..9ea87a414cfec29ca8edbf1d2964a82ff7eb7bde 100755 (executable)
@@ -11,7 +11,7 @@ TEST_POS=$3
 TEST_OP=$4
 TEST_FIN=$5
 
-if [ "$TEST_FIN" == "" ]; then
+if [ "x$TEST_FIN" = "x" ]; then
        TEST_FIN="finally";
 fi
 
index 884333b2accd748873009ebb8d6765c31824e362..08605a0f9cf29fca1648d502bb1e73b3d6839df4 100755 (executable)
@@ -12,7 +12,7 @@ TEST_LOAD_ARGS=$4
 TEST_INSTANCE_METHOD=$5
 TEST_EXTRA_STUFF=$6
 
-if [ "$TEST_INSTANCE_METHOD" == "instance" ]; then
+if [ "$TEST_INSTANCE_METHOD" = "instance" ]; then
        MEMBER_TEST_OP=$TEST_OP
        MEMBER_TEST_LOAD_ARGS=$TEST_LOAD_ARGS
        MEMBER_TEST_EXTRA_STUFF=$6
index 9e8894a709eb9ce5637d6cb040e5c37b59ad7e90..2687f0dfe687b95c2adf7b5a67b38d5de4cb7c9b 100755 (executable)
@@ -14,7 +14,7 @@ TEST_BEFORE_OP=$6
 
 echo $TEST_OP | grep unbox > /dev/null;
 
-if [ "$?" == "0" ]; then
+if [ $? -eq 0 ]; then
        TEST_CODE="
        ldloc.0
        box $TEST_TYPE";
index 008d485bedfb405f73a80212d3b7e52366041a33..5110b563ff63b3ca8c0b4f0cf2afcf2bf49c57e1 100755 (executable)
@@ -15,7 +15,7 @@ TEST_EXTRA_OPS=$6
 ZZ=`echo $TEST_TYPE1 | grep "\&"`
 T1_REF=$?
 
-if [ "$T1_REF" == "0" ]; then
+if [ $T1_REF -eq 0 ]; then
        T1_NO_REF=`echo $TEST_TYPE1 | cut -d '\' -f 1`
        INIT_LOCS=", $T1_NO_REF V_2"
        INIT_IL="ldloca.s 2\n\tstloc.0"
@@ -24,9 +24,9 @@ fi
 ZZ=`echo $TEST_TYPE2 | grep "\&"`
 T2_REF=$?
 
-if [ "$T2_REF" == "0" ]; then
+if [ $T2_REF -eq 0 ]; then
        T2_NO_REF=`echo $TEST_TYPE2 | cut -d '\' -f 1`
-       if [ "$T1_REF" == "0" ]; then
+       if [ $T1_REF -eq 0 ]; then
                INIT_LOCS="$INIT_LOCS , $T2_NO_REF V_3"
                INIT_IL="$INIT_IL \n\tldloca.s 3\n\tstloc.1"
        else
index e34c2fbe360238f2b8b8f28bf086f67327a50fee..b94b7e960bf38c25add04f1ed2177ab46c1e9c6e 100755 (executable)
@@ -14,7 +14,7 @@ TEST_EXTENDS=$6
 TEST_LOAD_BASE=$7
 
 
-if [ "$TEST_EXTENDS" == "yes" ]; then
+if [ "$TEST_EXTENDS" = "yes" ]; then
        TEST_EXTENDS="extends Owner\/Nested"
        TEST_CONSTRUCTOR="call instance void Owner\/Nested::.ctor()"
 else
@@ -22,7 +22,7 @@ else
        TEST_CONSTRUCTOR="call instance void object::.ctor()"
 fi
 
-if [ "$TEST_LOAD_BASE" == "yes" ]; then
+if [ "$TEST_LOAD_BASE" = "yes" ]; then
        TEST_LOAD_REF="ldarg.0"
 else
        TEST_LOAD_REF="call class Owner\/Nested Owner::Create ()"
index 81febde0c3046a92dd2316c866233f8d3b756ff8..6325f6167971059efb0444b3b09071e0ca490f70 100755 (executable)
@@ -13,7 +13,7 @@ TEST_TARGET_TYPE=$4
 TARGET_TYPE="Test"
 TEST_OTHER_CODE="call instance void TestClass::'.ctor'()"
 
-if [ "$TEST_TARGET_TYPE" == "other" ]; then
+if [ "$TEST_TARGET_TYPE" = "other" ]; then
        TARGET_TYPE="TestSubClass"
        TEST_OTHER_CODE=$TEST_CODE
        TEST_CODE=""
index a12b82c373a3279f9c89a3ed90403f7ee7f0d48c..31b8581fbe7f68025fde4127eb10511e796ab093 100755 (executable)
@@ -26,7 +26,7 @@ fi
 RET_2_LOCAL="$TEST_RET_TYPE2"
 RET_2_OP="ldloc 0"
 
-if [ "$TEST_RET_TYPE2" == "void" ]; then
+if [ "$TEST_RET_TYPE2" = "void" ]; then
        RET_2_LOCAL="int32"
        RET_2_OP="nop"
 fi
@@ -47,7 +47,7 @@ MANAGED_METHOD="
        }
 "
 
-if [ "$TEST_USE_NATIVE" == "pinvoke" ]; then
+if [ "$TEST_USE_NATIVE" = "pinvoke" ]; then
        LDFTN="ldftn $TCONV_2 ${TEST_RET_TYPE2} Driver::NativeMethod(${TEST_PARAM_TYPE2})"
        CALLVIRT="nop"
        MANAGED_METHOD=""
index 68bc551cf9fef66fbd3d9c291fb70dec22dc6daf..f6271e2fb9599ab7706dca36622187cf145fd1fc 100755 (executable)
@@ -16,7 +16,7 @@ TEST_NESTED_EXTENDS=$8
 TEST_LOAD_BASE=$9
 
 
-if [ "$TEST_BASE_EXTENDS" == "yes" ]; then
+if [ "$TEST_BASE_EXTENDS" = "yes" ]; then
        TEST_BASE_EXTENDS="extends Root"
        TEST_BASE_CONSTRUCTOR="call instance void Root::.ctor()"
 else
@@ -24,7 +24,7 @@ else
        TEST_BASE_CONSTRUCTOR="call instance void object::.ctor()"
 fi
 
-if [ "$TEST_NESTED_EXTENDS" == "yes" ]; then
+if [ "$TEST_NESTED_EXTENDS" = "yes" ]; then
        TEST_NESTED_EXTENDS="extends Root\/Nested"
        TEST_NESTED_CONSTRUCTOR="call instance void Root\/Nested::.ctor()"
 else
@@ -32,7 +32,7 @@ else
        TEST_NESTED_CONSTRUCTOR="call instance void object::.ctor()"
 fi
 
-if [ "$TEST_LOAD_BASE" == "yes" ]; then
+if [ "$TEST_LOAD_BASE" = "yes" ]; then
        TEST_LOAD_REF="ldarg.0"
 else
        TEST_LOAD_REF="call class Root\/Nested Root::Create ()"
index 284fadfd7e6d81c92e8bfb7c4ef7dc0887bbe103..0647eed5b19b73bad74a5401a8d7469b508a0dc7 100755 (executable)
@@ -12,7 +12,7 @@ TEST_BLOCK_2=$4
 TEST_WITH_FILTER_BLOCK=$5
 TEST_WITH_FINALLY_BLOCK=$6
 
-if [ "$TEST_WITH_FILTER_BLOCK" == "yes" ]; then
+if [ "$TEST_WITH_FILTER_BLOCK" = "yes" ]; then
        FILTER_BLOCK="
 FILTER_BLOCK_3:
        nop
@@ -35,7 +35,7 @@ else
        FILTER_BLOCK="";
 fi
 
-if [ "$TEST_WITH_FINALLY_BLOCK" == "yes" ]; then
+if [ "$TEST_WITH_FINALLY_BLOCK" = "yes" ]; then
        FINALLY_BLOCK="
 FINALLY_BLOCK_1:
        nop
index a50a5f4385c692cdc1fdf7068b681172c4cb40c9..8d72117ffc2918268a9c31695a832234e63e1f5f 100755 (executable)
@@ -11,7 +11,7 @@ TEST_OP=$3
 TEST_TYPE1=$4
 TEST_TYPE2=$5
 TEST_EMIT_CSTOR=$6
-if [ "${TEST_EMIT_CSTOR}" == "yes" ]; then
+if [ "${TEST_EMIT_CSTOR}" = "yes" ]; then
        TEST_CSTOR="newobj instance void ${TEST_TYPE2}::.ctor()";
 else
        TEST_CSTOR="ldloc.0";
index 3382ff99d6e279d332f4f7e4e5b312ca3a35330d..5b1e064afaa1862cffca7723282e622fcd79131f 100755 (executable)
@@ -14,7 +14,7 @@ ZZ=`echo $TEST_TYPE1 | grep "\&"`
 T1_REF=$?
 
 LOCAL_INIT="";
-if [ "$T1_REF" == "0" ]; then
+if [ $T1_REF -eq 0 ]; then
        T1_NO_REF=`echo $TEST_TYPE1 | cut -d '\' -f 1`
        INIT_LOCS=", $T1_NO_REF V_0"
        INIT_IL="ldloca.s 1\n\tstloc.0"
index c314cf297020215183136ba7073d23d29d2d9091..4a2f84a1ed6bd0796a57d3071e6bc7127ebf404d 100755 (executable)
@@ -13,7 +13,7 @@ ZZ=`echo $TEST_TYPE1 | grep "\&"`
 T1_REF=$?
 
 LOCAL_INIT="";
-if [ "$T1_REF" == "0" ]; then
+if [ $T1_REF -eq 0 ]; then
        T1_NO_REF=`echo $TEST_TYPE1 | cut -d '\' -f 1`
        INIT_LOCS=", $T1_NO_REF V_0"
        INIT_IL="ldloca.s 1\n\tstloc.0"
index 8a5016a7fd1d9b05af28ec1c5f38dd24f09d037c..e53849cf18cdf7ef5c216834689978a169786f81 100755 (executable)
@@ -16,14 +16,14 @@ TRY_END="
                leave END
        }"
 
-if [ "$TEST_BLOCK" == "catch" ]; then
+if [ "$TEST_BLOCK" = "catch" ]; then
        TRY_MIDDLE="
                leave END
        } catch [mscorlib]System.NullReferenceException {"
        TRY_END="
                leave END
        }"
-elif [ "$TEST_BLOCK" == "filter" ]; then
+elif [ "$TEST_BLOCK" = "filter" ]; then
        TRY_MIDDLE="
                leave END
        } filter {"
@@ -34,7 +34,7 @@ elif [ "$TEST_BLOCK" == "filter" ]; then
        } {
                leave END
        }"
-elif [ "$TEST_BLOCK" == "handler" ]; then
+elif [ "$TEST_BLOCK" = "handler" ]; then
        TRY_MIDDLE="
                leave END
        } filter {
@@ -45,14 +45,14 @@ elif [ "$TEST_BLOCK" == "handler" ]; then
        TRY_END="
                leave END
        }"
-elif [ "$TEST_BLOCK" == "finally" ]; then
+elif [ "$TEST_BLOCK" = "finally" ]; then
        TRY_MIDDLE="
                leave END
        } finally {"
        TRY_END="
                endfinally
        }"
-elif [ "$TEST_BLOCK" == "fault" ]; then
+elif [ "$TEST_BLOCK" = "fault" ]; then
        TRY_MIDDLE="
                leave END
        } fault {"
index d096e85256619db690df7a107f9561fe4fbc7fe1..5fd41668a68d9a3de2ddd20729a57698a6822095 100755 (executable)
@@ -12,7 +12,7 @@ TEST_CLASS_ACCESS=$4
 TEST_MEMBER_ACCESS=$5
 TEST_EXTENDS=$6
 
-if [ "$TEST_EXTENDS" == "yes" ]; then
+if [ "$TEST_EXTENDS" = "yes" ]; then
        TEST_EXTENDS="extends Owner"
        TEST_CONSTRUCTOR="call instance void Owner::.ctor()"
 else
@@ -108,4 +108,4 @@ $SED -e "s/VALIDITY/${TEST_VALIDITY}/g" -e "s/OPCODE/${TEST_OP}/g" -e "s/CONSTRU
        ldc.i4.0
        ret
 }
-//EOF
\ No newline at end of file
+//EOF
index f0d53366c87aead38e91afaadbbe1f8353553b04..6390c65695cdd7145260c10e6adae930871ced95 100755 (executable)
@@ -18,7 +18,7 @@ echo $TEST_FILE
 TEST_TYPE1=`echo $TEST_TYPE1 | $SED -s 's/&/\\\&/'`
 TEST_TYPE2=`echo $TEST_TYPE2 | $SED -s 's/&/\\\&/'`
 
-if [ "$TEST_CREATE_FIELD" == "no" ]; then
+if [ "$TEST_CREATE_FIELD" = "no" ]; then
        CLASS_FIELDS="";
 else
        CLASS_FIELDS=".field public ${TEST_TYPE1} fld\n .field public static ${TEST_TYPE1} sfld";
index baa46d38ae6d56e4973925cadeb8f8089763783c..239e27dc3b94c1fc0637879f4b3a655bbc46f86c 100755 (executable)
@@ -12,7 +12,7 @@ TEST_POS_1=$4
 TEST_POS_2=$5
 TEST_TYPE_0=$6
 
-if [ "$TEST_TYPE_0" == "" ] ; then
+if [ "x$TEST_TYPE_0" = "x" ] ; then
        TEST_TYPE_0="int32";
 fi
 
index 1bf078b35dd01625e2ca7b2c5a77be047a346a5e..d1859623b24e494a819f8769bf3e8fb7998d4b4f 100755 (executable)
@@ -16,7 +16,7 @@ ZZ=`echo $TEST_TYPE2 | grep "\&"`
 T2_REF=$?
 
 LOCAL_INIT="";
-if [ "$T2_REF" == "0" ]; then
+if [ $T2_REF -eq 0 ]; then
        T2_NO_REF=`echo $TEST_TYPE2 | cut -d '\' -f 1`
        INIT_LOCS=", $T2_NO_REF V_2"
        INIT_IL="ldloca.s 2\n\tstloc.1"
index 1767aa4816631a4d8c28061df434dab841a41e45..face162ef8ee56ef18209a364c00119c1f8c2f43 100755 (executable)
@@ -12,7 +12,7 @@ TEST_EXTRA=$4
 TEST_OP=$5
 TEST_FIN=$6
 
-if [ "$TEST_FIN" == "" ]; then
+if [ "x$TEST_FIN" = "x" ]; then
        TEST_FIN="finally";
 fi
 
index de58fa79f35f1a48a4231b067adf06ebb88a9061..82bdccdf81dedc4cb923d7e986e153440d03388d 100755 (executable)
@@ -12,7 +12,7 @@ TEST_LOAD_OP=$4
 TEST_TYPE=$5
 TEST_RET_TYPE=$6
 
-if [ "$TEST_RET_TYPE" == "" ]; then
+if [ "x$TEST_RET_TYPE" = "x" ]; then
        TEST_RET_TYPE="void"
 else
        LD_RET_CODE="ldloc.0"
index 270c2677b865aa6ed8f5c8ef218186c33b2ba785..25dd54a92576e995e679a27356d15ee6c9f19bea 100755 (executable)
@@ -25,7 +25,7 @@ done
 I=1
 for OP in add div mul rem sub
 do
-  if [ "$OP" == "div" ] || [ "$OP" == "rem" ]; then
+  if [ "$OP" = "div" ] || [ "$OP" = "rem" ]; then
        INIT="yes";
   else
        INIT="no";
@@ -92,7 +92,7 @@ done
 I=1
 for OP in div mul rem
 do
-  if [ "$OP" == "div" ] || [ "$OP" == "div" ]; then
+  if [ "$OP" = "div" ] || [ "$OP" = "div" ]; then
        INIT="yes";
   else
        INIT="no";
@@ -112,7 +112,7 @@ done
 I=1
 for OP in div mul rem add
 do
-  if [ "$OP" == "div" ] || [ "$OP" == "div" ]; then
+  if [ "$OP" = "div" ] || [ "$OP" = "div" ]; then
        INIT="yes";
   else
        INIT="no";
@@ -503,9 +503,9 @@ function fix () {
                A=$1;
        fi
 
-       if [ "$A" == "bool&" ]; then
+       if [ "$A" = "bool&" ]; then
                A="int8&";
-       elif [ "$A" == "char&" ]; then
+       elif [ "$A" = "char&" ]; then
                A="int16&";
        fi
 
@@ -522,11 +522,11 @@ do
                do
                        TA="$(fix $TYPE1)"
                        TB="$(fix $TYPE2)"
-                       if [ "$TA" == "$TB" ]; then
+                       if [ "$TA" = "$TB" ]; then
                                ./make_store_test.sh ref_coercion_${I} valid "$OP" "$TYPE1" "$TYPE2"
-                       elif [ "$TA" == "int32&" ] && [ "$TB" == "int&" ]; then
+                       elif [ "$TA" = "int32&" ] && [ "$TB" = "int&" ]; then
                                ./make_store_test.sh ref_coercion_${I} valid "$OP" "$TYPE1" "$TYPE2"
-                       elif [ "$TA" == "int&" ] && [ "$TB" == "int32&" ]; then
+                       elif [ "$TA" = "int&" ] && [ "$TB" = "int32&" ]; then
                                ./make_store_test.sh ref_coercion_${I} valid "$OP" "$TYPE1" "$TYPE2"
                        else
                                ./make_store_test.sh ref_coercion_${I} unverifiable "$OP" "$TYPE1" "$TYPE2"
@@ -545,7 +545,7 @@ do
                do
                        TA="$(fix $TYPE1)"
                        TB="$(fix $TYPE2)"
-                       if [ "$TA" == "$TB" ]; then
+                       if [ "$TA" = "$TB" ]; then
                                ./make_store_test.sh ref_coercion_${I} valid "$OP" "$TYPE1" "$TYPE2"
                        else
                                ./make_store_test.sh ref_coercion_${I} unverifiable "$OP" "$TYPE1" "$TYPE2"
@@ -561,7 +561,7 @@ do
        do
                for TYPE2 in 'class ClassA&' 'class ClassB&' 'class InterfaceA&' 'class InterfaceB&' 'class ValueType&'
                do
-                       if [ "$TYPE1" == "$TYPE2" ]; then
+                       if [ "$TYPE1" = "$TYPE2" ]; then
                                ./make_store_test.sh ref_coercion_${I} valid "$OP" "$TYPE1" "$TYPE2"
                        else
                                ./make_store_test.sh ref_coercion_${I} unverifiable "$OP" "$TYPE1" "$TYPE2"
@@ -791,17 +791,17 @@ do
        ZZ=`echo $TYPE2 | grep "*";`
        T2_PTR=$?
        
-    if (($T1_PTR == 0  ||  $T2_PTR == 0)); then
+    if [ $T1_PTR -eq 0 ] || [ $T2_PTR -eq 0 ]; then
                ./make_stack_merge_test.sh stack_merge_${I} unverifiable "$TYPE1" "$TYPE2"
-    elif [ "$TYPE1" == "$TYPE2" ]; then
+    elif [ "$TYPE1" = "$TYPE2" ]; then
                ./make_stack_merge_test.sh stack_merge_${I} valid "$TYPE1" "$TYPE2"
-       elif [ "$TYPE1" == "int32" ] && [ "$TYPE2" == "native int" ]; then
+       elif [ "$TYPE1" = "int32" ] && [ "$TYPE2" = "native int" ]; then
                ./make_stack_merge_test.sh stack_merge_${I} valid "$TYPE1" "$TYPE2"
-       elif [ "$TYPE1" == "native int" ] && [ "$TYPE2" == "int32" ]; then
+       elif [ "$TYPE1" = "native int" ] && [ "$TYPE2" = "int32" ]; then
                ./make_stack_merge_test.sh stack_merge_${I} valid "$TYPE1" "$TYPE2"
-       elif [ "$TYPE1" == "int32&" ] && [ "$TYPE2" == "native int&" ]; then
+       elif [ "$TYPE1" = "int32&" ] && [ "$TYPE2" = "native int&" ]; then
                ./make_stack_merge_test.sh stack_merge_${I} valid "$TYPE1" "$TYPE2"
-       elif [ "$TYPE1" == "native int&" ] && [ "$TYPE2" == "int32&" ]; then
+       elif [ "$TYPE1" = "native int&" ] && [ "$TYPE2" = "int32&" ]; then
                ./make_stack_merge_test.sh stack_merge_${I} valid "$TYPE1" "$TYPE2"
        else
                ./make_stack_merge_test.sh stack_merge_${I} unverifiable "$TYPE1" "$TYPE2"
@@ -1335,7 +1335,7 @@ do
        MAX_PARAM_RESULT="unverifiable"
        POPS="pop\npop\npop\npop\npop\npop\npop\npop\n"
        
-       if [ "$OP" == "ldloc" ]; then
+       if [ "$OP" = "ldloc" ]; then
                MAX_PARAM_RESULT="invalid"
 
                LOCALS_1=$ARGS_1
@@ -1892,7 +1892,7 @@ function create_nesting_test_same_result () {
       do
         for LOAD in yes no
         do
-          if ! ( [ "$NESTED" == "no" ] && [ "$LOAD" == "yes" ] ) ; then
+          if ! ( [ "$NESTED" = "no" ] && [ "$LOAD" = "yes" ] ) ; then
             ./make_double_nesting_test.sh double_nesting_access_check_${K}_$I $2 "$OP" $3 $4 $5 "$BASE" "$NESTED" "$LOAD"
             K=`expr $K + 1`
           fi
@@ -1910,9 +1910,9 @@ function create_nesting_test_only_first_ok () {
       do
         for LOAD in yes no
         do
-          if ! ( [ "$NESTED" == "no" ] && [ "$LOAD" == "yes" ] ) ; then
+          if ! ( [ "$NESTED" = "no" ] && [ "$LOAD" = "yes" ] ) ; then
               EXPECT=unverifiable
-           if [ "$FIRST" == "$K" ]; then
+           if [ "$FIRST" = "$K" ]; then
               EXPECT=valid
            fi
            ./make_double_nesting_test.sh double_nesting_access_check_${K}_$I $EXPECT "$OP" $2 $3 $4 "$BASE" "$NESTED" "$LOAD"
@@ -2065,7 +2065,7 @@ function create_nesting_test_strips_result_static () {
     for NESTED in yes no
       do
         EXPECT=unverifiable
-        if [ "$NESTED" == "yes" ]; then
+        if [ "$NESTED" = "yes" ]; then
           EXPECT=valid
         fi
         ./make_double_nesting_test.sh double_nesting_access_check_${K}_$I $EXPECT "$OP" $2 $3 $4 "$BASE" "$NESTED" yes
@@ -2188,9 +2188,9 @@ function fix_ldobj () {
                A=$1;
        fi
 
-       if [ "$A" == "bool" ]; then
+       if [ "$A" = "bool" ]; then
                A="int8";
-       elif [ "$A" == "char" ]; then
+       elif [ "$A" = "char" ]; then
                A="int16";
        fi
 
@@ -2207,7 +2207,7 @@ do
        do
                TYPE1="$(fix_ldobj $T1)"
                TYPE2="$(fix_ldobj $T2)"
-               if [ "$TYPE1" == "$TYPE2" ] ; then
+               if [ "$TYPE1" = "$TYPE2" ] ; then
                        ./make_ldobj_test.sh ldobj_${I} valid "${T1}\&" "${T2}"
                else
                        ./make_ldobj_test.sh ldobj_${I} unverifiable "${T1}\&" "${T2}"
@@ -2564,7 +2564,7 @@ I=1
 for TYPE1 in "int8" "bool" "int16" "char" "int32" "int64" "float64" "native int" "object" "string" "class Class" "valuetype MyStruct"  "int32[]" "int32[,]" "int32*" "method int32 *(int32)"  "class Template\`1<object>"
 do
        ./make_store_indirect_test.sh indirect_store_bad_addr_r4_${I} unverifiable "stind.r4" "${TYPE1}\&" "float32"
-       if [ "$TYPE1" == "float64" ]; then
+       if [ "$TYPE1" = "float64" ]; then
                ./make_store_indirect_test.sh indirect_store_good_val_r4_${I} valid "stind.r4" "float32\&" "${TYPE1}"
        else
                ./make_store_indirect_test.sh indirect_store_bad_val_r4_${I} unverifiable "stind.r4" "float32\&" "${TYPE1}"
@@ -2577,7 +2577,7 @@ I=1
 for TYPE1 in "int8" "bool" "int16" "char" "int32" "int64" "float32" "native int" "object" "string" "class Class" "valuetype MyStruct"  "int32[]" "int32[,]" "int32*" "method int32 *(int32)"  "class Template\`1<object>"
 do
        ./make_store_indirect_test.sh indirect_store_bad_addr_r8_${I} unverifiable "stind.r8" "${TYPE1}\&" "float64"
-       if [ "$TYPE1" == "float32" ]; then
+       if [ "$TYPE1" = "float32" ]; then
                ./make_store_indirect_test.sh indirect_store_good_val_r8_${I} valid "stind.r8" "float64\&" "${TYPE1}";
        else
                ./make_store_indirect_test.sh indirect_store_bad_val_r8_${I} unverifiable "stind.r8" "float64\&" "${TYPE1}";
@@ -3223,30 +3223,34 @@ done
 
 # Exception block branch tests (see 2.19)
 
-for I in {1..2};
+I=1; while [ $I -le 2 ]
 do
        ./make_rethrow_test.sh rethrow_from_catch_${I} invalid ${I}
+       I=$((I + 1))
 done
 
-for I in {3..10};
+I=3; while [ $I -le 10 ]
 do
        ./make_rethrow_test.sh rethrow_from_catch_${I} valid ${I}
+       I=$((I + 1))
 done
 
 
 
 # endfinally / endfault
 
-for I in {1..7};
+I=1; while [ $I -le 7 ]
 do
        ./make_endfinally_test.sh endfinally_block_${I} invalid finally ${I}
        ./make_endfinally_test.sh endfault_block_${I} invalid fault ${I}
+       I=$((I + 1))
 done
 
-for I in {8..9};
+I=8; while [ $I -le 9 ]
 do
        ./make_endfinally_test.sh endfinally_block_${I} valid finally ${I}
        ./make_endfinally_test.sh endfault_block_${I} valid fault ${I}
+       I=$((I + 1))
 done
 
 #stack can have stuff and endfinally or endfault will just empty it
@@ -3268,7 +3272,7 @@ done
 ./make_endfilter_test.sh endfilter_inside_protected_block_3 invalid 3 "ldc.i4.1\n\t\tendfilter"
 ./make_endfilter_test.sh endfilter_inside_protected_block_5 strict 5 "ldc.i4.1\n\t\tendfilter"
 
-for I in {2,4,6};
+for I in 2 4 6;
 do
        ./make_endfilter_test.sh endfilter_inside_protected_block_${I} unverifiable ${I} "ldc.i4.1\n\t\tendfilter"
 done
@@ -3302,9 +3306,9 @@ EXTRA="ldloc.0\n\tbrfalse END"
 ./make_leave_test.sh "filter_block_test_1" valid "1" "leave END" "$EXTRA"
 
 #but not ok to leave finally or filter
-for I in {2..3};
-do
+I=2; while [ $I -le 3 ]; do
        ./make_leave_test.sh "filter_block_test_${I}" unverifiable "${I}" "leave END" "${EXTRA}_${I}"
+       I=$((I + 1))
 done
 
 #neither is to branch to invalid regions of code
@@ -3314,24 +3318,27 @@ done
 
 # br.X
 #valid tests
-for I in {1..6}; do
+I=1; while [ $I -le 6 ]; do
        ./make_branch_test.sh branch_inside_same_block_${I} valid ${I} "br BLOCK_${I}";
        ./make_branch_test.sh branch_inside_same_block_${I}_s valid ${I} "br.s BLOCK_${I}";
+       I=$((I + 1))
 done
 
 #branching outside of the protected block
-for I in {2..6}; do
+I=2; while [ $I -le 6 ]; do
        ./make_branch_test.sh branch_outside_protected_block_${I} unverifiable ${I} "br END";
+       I=$((I + 1))
 done
 
 #branching to a protected block from the outside
-for I in {2..6}; do
-       if [ "$I" == "4" ]; then
+I=2; while [ $I -le 6 ]; do
+       if [ $I -eq 4 ]; then
                ./make_branch_test.sh branch_inside_protected_block_from_outside_${I}_finally invalid 1 "br BLOCK_${I}" "finally";
                ./make_branch_test.sh branch_inside_protected_block_from_outside_${I}_fault invalid 1 "br BLOCK_${I}" "fault";
        else
                ./make_branch_test.sh branch_inside_protected_block_from_outside_${I} unverifiable 1 "br BLOCK_${I}";
        fi
+       I=$((I + 1))
 done
 
 
@@ -3349,25 +3356,28 @@ done
 #TODO test the encoding of the switch table
 # switch
 #valid tests
-for I in {1..6}; do
+I=1; while [ $I -le 6 ]; do
        ./make_switch_test.sh switch_inside_same_block_${I} valid ${I} "ldloc.0" "switch (BLOCK_${I}, BLOCK_${I}_B)";
+       I=$((I + 1))
 done
 
 ./make_switch_test.sh switch_with_native_int_on_stack valid 1 "ldloc.1" "switch (BLOCK_1, BLOCK_1_B)";
 
 #branching outside of the protected block
-for I in {2..6}; do
+I=2; while [ $I -le 6 ]; do
        ./make_switch_test.sh switch_outside_protected_block_${I} unverifiable ${I} "ldloc.0" "switch (END, BLOCK_1, BLOCK_1_B)";
+       I=$((I + 1))
 done
 
 #branching to a protected block from the outside
-for I in {2..6}; do
-       if [ "$I" == "4" ]; then
+I=2; while [ $I -le 6 ]; do
+       if [ $I -eq 4 ]; then
                ./make_switch_test.sh switch_inside_protected_block_from_outside_${I}_finally invalid 1 "ldloc.0" "switch (BLOCK_${I}, BLOCK_${I}_B)" "finally";
                ./make_switch_test.sh switch_inside_protected_block_from_outside_${I}_fault invalid 1 "ldloc.0" "switch (BLOCK_${I}, BLOCK_${I}_B)" "fault";
        else
                ./make_switch_test.sh switch_inside_protected_block_from_outside_${I} unverifiable 1 "ldloc.0" "switch (BLOCK_${I}, BLOCK_${I}_B)";
        fi
+       I=$((I + 1))
 done
 
 #TODO branching out of range (FIX ilasm first)
@@ -4893,33 +4903,38 @@ done
 ./make_overlapped_test.sh ref_only_overlapping_5 invalid 0 0 8 int32
 
 #invalid opcodes
-for I in {166..178}
+I=166; while [ $I -le 178 ]
 do
        ./make_bad_op_test.sh bad_op_$I invalid $I
+       I=$((I + 1))
 done
 
 
-for I in {187..193}
+I=187; while [ $I -le 193 ]
 do
        ./make_bad_op_test.sh bad_op_$I invalid $I
+       I=$((I + 1))
 done
 
-for I in {196..207}
+I=196; while [ $I -le 207 ]
 do
        ./make_bad_op_test.sh bad_op_$I invalid $I
+       I=$((I + 1))
 done
 
-for I in {225..253}
+I=225; while [ $I -le 253 ]
 do
        ./make_bad_op_test.sh bad_op_$I invalid $I
+       I=$((I + 1))
 done
 
 ./make_bad_op_test.sh bad_op_xff invalid 255
 
 
-for I in {35..255}
+I=35; while [ $I -le 255 ]
 do
        ./make_bad_op_test.sh bad_op_with_prefix_$I invalid 0xFE $I
+       I=$((I + 1))
 done
 
 
@@ -5148,5 +5163,3 @@ done
 
 ./make_generic_argument_constraints_test.sh type_mixed_3 valid "" "(IfaceA)"
 ./make_generic_argument_constraints_test.sh type_mixed_4 valid "" "class (IfaceA)"
-
-
index b71063657cbc3083f621f7d0d5cddd78c7348391..744e931a2a9ad8a213c411c8de4509647c75d7d4 100755 (executable)
@@ -12,7 +12,7 @@ TEST_TYPE2=$4
 TEST_POST_OP=$5
 TEST_NO_BOX=$6
 TEST_BOX="box ${TEST_TYPE1}";
-if [ "${TEST_NO_BOX}" == "yes" ]; then
+if [ "x${TEST_NO_BOX}" = "xyes" ]; then
        TEST_BOX="";
 fi
 
index c5303a1a6cd7b3060fae2b5be3aeeaa1815d952b..32d859c50d56cee18c92a9518db37a9c762a0597 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 2fb1498f60995e14dde7add344b9f5722e030ec2..07c33a90eff324a61714991810a62093243072a1 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2013 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index fd916a659061434fe2f093a56469eeb23170509a..3438039a4b0cb91900fa6e057be353b38b47e04b 100644 (file)
@@ -5,6 +5,7 @@
  *   Aleksey Kliger <aleksey@xamarin.com>
  *
  * Copyright 2015 Xamarin, Inc. (www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 951b1b7321bb04a0f35ef4d9408308265748ac41..7cc6b627445a683c4af6a12971246b36ab28864a 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2013 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 447af4e8995727ef2a353acbeb766b5110127109..86afad502ffe27947c4bf7718bc49abbd4ded33c 100644 (file)
@@ -503,10 +503,56 @@ InterlockedCompareExchange64(volatile gint64 *dest, gint64 exch, gint64 comp)
        return __sync_val_compare_and_swap (dest, comp, exch);
 }
 
-#elif defined (HAVE_64BIT_CMPXCHG_FALLBACK)
+#elif defined (__arm__) && defined (HAVE_ARMV7) && (defined(TARGET_IOS) || defined(TARGET_WATCHOS) || defined(TARGET_ANDROID))
+
+#if defined (TARGET_IOS) || defined (TARGET_WATCHOS)
+
+#ifndef __clang__
+#error "Not supported."
+#endif
+
+gint64
+InterlockedCompareExchange64(volatile gint64 *dest, gint64 exch, gint64 comp)
+{
+       return  __sync_val_compare_and_swap (dest, comp, exch);
+}
+
+#elif defined (TARGET_ANDROID)
+
+/* Some Android systems can't find the 64-bit CAS intrinsic at runtime,
+ * so we have to roll our own...
+ */
+
+gint64 InterlockedCompareExchange64(volatile gint64 *dest, gint64 exch, gint64 comp) __attribute__ ((naked));
+
+gint64
+InterlockedCompareExchange64(volatile gint64 *dest, gint64 exch, gint64 comp)
+{
+       __asm__ (
+               "push           {r4, r5, r6, r7}\n"
+               "ldrd           r4, [sp, #16]\n"
+               "dmb            sy\n"
+       "1:\n"
+               "ldrexd         r6, [r0]\n"
+               "cmp            r7, r5\n"
+               "cmpeq          r6, r4\n"
+               "bne            2f\n"
+               "strexd         r1, r2, [r0]\n"
+               "cmp            r1, #0\n"
+               "bne            1b\n"
+       "2:\n"
+               "dmb            sy\n"
+               "mov            r0, r6\n"
+               "mov            r1, r7\n"
+               "pop            {r4, r5, r6, r7}\n"
+               "bx                     lr\n"
+       );
+}
+
+#else
+
+#error "Need a 64-bit CAS fallback!"
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/utils/atomic.c"
 #endif
 
 #else
index 306800cfe1d0cd508a56aafb341a815de949233c..4f5f010afd31bd61551347f754fe9f31639b0bae 100755 (executable)
@@ -6,6 +6,7 @@
  *
  * (C) 2002 Ximian, Inc.
  * Copyright 2012 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef _WAPI_ATOMIC_H_
 #include "config.h"
 #include <glib.h>
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/utils/atomic.h"
-#endif
+/*
+The current Nexus 7 arm-v7a fails with:
+F/MonoDroid( 1568): shared runtime initialization error: Cannot load library: reloc_library[1285]:    37 cannot locate '__sync_val_compare_and_swap_8'
+
+Apple targets have historically being problematic, xcode 4.6 would miscompile the intrinsic.
+*/
 
 /* On Windows, we always use the functions provided by the Windows API. */
 #if defined(__WIN32__) || defined(_WIN32)
index 624d1b88b8eb595500bcdad638d007d56f026ffe..f4ae1b54100e4550201e99c71ecf673951f815a8 100644 (file)
@@ -8,7 +8,7 @@
  */
 #include <config.h>
 
-#ifdef CHECKED_BUILD
+#ifdef ENABLE_CHECKED_BUILD
 
 #include <mono/utils/checked-build.h>
 #include <mono/utils/mono-threads.h>
 #include <execinfo.h>
 #endif
 
+// Selective-enable support
+
+// Returns true for check modes which are allowed by both the current DISABLE_ macros and the MONO_CHECK_MODE env var.
+// Argument may be a bitmask; if so, result is true if at least one specified mode is enabled.
+mono_bool
+mono_check_mode_enabled (MonoCheckMode query)
+{
+       static MonoCheckMode check_mode = MONO_CHECK_MODE_UNKNOWN;
+       if (G_UNLIKELY (check_mode == MONO_CHECK_MODE_UNKNOWN))
+       {
+               MonoCheckMode env_check_mode = MONO_CHECK_MODE_NONE;
+               const gchar *env_string = g_getenv ("MONO_CHECK_MODE");
+
+               if (env_string)
+               {
+                       gchar **env_split = g_strsplit (env_string, ",", 0);
+                       for (gchar **env_component = env_split; *env_component; env_component++)
+                       {
+                               mono_bool check_all = g_str_equal (*env_component, "all");
+#ifdef ENABLE_CHECKED_BUILD_GC
+                               if (check_all || g_str_equal (*env_component, "gc"))
+                                       env_check_mode |= MONO_CHECK_MODE_GC;
+#endif
+#ifdef ENABLE_CHECKED_BUILD_METADATA
+                               if (check_all || g_str_equal (*env_component, "metadata"))
+                                       env_check_mode |= MONO_CHECK_MODE_METADATA;
+#endif
+#ifdef ENABLE_CHECKED_BUILD_THREAD
+                               if (check_all || g_str_equal (*env_component, "thread"))
+                                       env_check_mode |= MONO_CHECK_MODE_THREAD;
+#endif
+                       }
+                       g_strfreev (env_split);
+               }
+
+               check_mode = env_check_mode;
+       }
+       return check_mode & query;
+}
+
+static int
+mono_check_transition_limit (void)
+{
+       static int transition_limit = -1;
+       if (transition_limit < 0) {
+               const gchar *env_string = g_getenv ("MONO_CHECK_THREAD_TRANSITION_HISTORY");
+               if (env_string)
+                       transition_limit = atoi (env_string);
+               else
+                       transition_limit = 3;
+       }
+       return transition_limit;
+}
+
 typedef struct {
        GPtrArray *transitions;
        guint32 in_gc_critical_region;
@@ -34,7 +88,9 @@ static MonoNativeTlsKey thread_status;
 void
 checked_build_init (void)
 {
-       mono_native_tls_alloc (&thread_status, NULL);
+       // Init state for get_state, which can be called either by gc or thread mode
+       if (mono_check_mode_enabled (MONO_CHECK_MODE_GC | MONO_CHECK_MODE_THREAD))
+               mono_native_tls_alloc (&thread_status, NULL);
 }
 
 static CheckState*
@@ -50,11 +106,11 @@ get_state (void)
        return state;
 }
 
-#if !defined(DISABLE_CHECKED_BUILD_THREAD)
+#ifdef ENABLE_CHECKED_BUILD_THREAD
 
 #define MAX_NATIVE_BT 6
 #define MAX_NATIVE_BT_PROBE (MAX_NATIVE_BT + 5)
-#define MAX_TRANSITIONS 3
+#define MAX_TRANSITIONS (mono_check_transition_limit ())
 
 #ifdef HAVE_BACKTRACE_SYMBOLS
 
@@ -124,6 +180,9 @@ free_transition (ThreadTransition *t)
 void
 checked_build_thread_transition (const char *transition, void *info, int from_state, int suspend_count, int next_state, int suspend_count_delta)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_THREAD))
+               return;
+
        MonoThreadInfo *cur = mono_thread_info_current_unchecked ();
        CheckState *state = get_state ();
        /* We currently don't record external changes as those are hard to reason about. */
@@ -143,16 +202,11 @@ checked_build_thread_transition (const char *transition, void *info, int from_st
        g_ptr_array_add (state->transitions, t);
 }
 
-#endif /* !defined(DISABLE_CHECKED_BUILD_THREAD) */
-
-#if !defined(DISABLE_CHECKED_BUILD_GC)
-
-static void
-assertion_fail (const char *msg, ...)
+void
+mono_fatal_with_history (const char *msg, ...)
 {
        int i;
        GString* err = g_string_sized_new (100);
-       CheckState *state = get_state ();
 
        g_string_append_printf (err, "Assertion failure in thread %p due to: ", mono_native_thread_id_get ());
 
@@ -161,52 +215,67 @@ assertion_fail (const char *msg, ...)
        g_string_append_vprintf (err, msg, args);
        va_end (args);
 
-       g_string_append_printf (err, "\nLast %d state transitions: (most recent first)\n", state->transitions->len);
-
-       for (i = state->transitions->len - 1; i >= 0; --i) {
-               ThreadTransition *t = state->transitions->pdata [i];
-               char *bt = translate_backtrace (t->backtrace, t->size);
-               g_string_append_printf (err, "[%s] %s -> %s (%d) %s%d at:\n%s",
-                       t->name,
-                       mono_thread_state_name (t->from_state),
-                       mono_thread_state_name (t->next_state),
-                       t->suspend_count,
-                       t->suspend_count_delta > 0 ? "+" : "", //I'd like to see this sort of values: -1, 0, +1
-                       t->suspend_count_delta,
-                       bt);
-               g_free (bt);
+       if (mono_check_mode_enabled (MONO_CHECK_MODE_THREAD))
+       {
+               CheckState *state = get_state ();
+
+               g_string_append_printf (err, "\nLast %d state transitions: (most recent first)\n", state->transitions->len);
+
+               for (i = state->transitions->len - 1; i >= 0; --i) {
+                       ThreadTransition *t = state->transitions->pdata [i];
+                       char *bt = translate_backtrace (t->backtrace, t->size);
+                       g_string_append_printf (err, "[%s] %s -> %s (%d) %s%d at:\n%s",
+                               t->name,
+                               mono_thread_state_name (t->from_state),
+                               mono_thread_state_name (t->next_state),
+                               t->suspend_count,
+                               t->suspend_count_delta > 0 ? "+" : "", //I'd like to see this sort of values: -1, 0, +1
+                               t->suspend_count_delta,
+                               bt);
+                       g_free (bt);
+               }
        }
 
        g_error (err->str);
        g_string_free (err, TRUE);
 }
 
+#endif /* defined(ENABLE_CHECKED_BUILD_THREAD) */
+
+#ifdef ENABLE_CHECKED_BUILD_GC
+
 void
 assert_gc_safe_mode (void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        MonoThreadInfo *cur = mono_thread_info_current ();
        int state;
 
        if (!cur)
-               assertion_fail ("Expected GC Safe mode but thread is not attached");
+               mono_fatal_with_history ("Expected GC Safe mode but thread is not attached");
 
        switch (state = mono_thread_info_current_state (cur)) {
        case STATE_BLOCKING:
        case STATE_BLOCKING_AND_SUSPENDED:
                break;
        default:
-               assertion_fail ("Expected GC Safe mode but was in %s state", mono_thread_state_name (state));
+               mono_fatal_with_history ("Expected GC Safe mode but was in %s state", mono_thread_state_name (state));
        }
 }
 
 void
 assert_gc_unsafe_mode (void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        MonoThreadInfo *cur = mono_thread_info_current ();
        int state;
 
        if (!cur)
-               assertion_fail ("Expected GC Unsafe mode but thread is not attached");
+               mono_fatal_with_history ("Expected GC Unsafe mode but thread is not attached");
 
        switch (state = mono_thread_info_current_state (cur)) {
        case STATE_RUNNING:
@@ -214,18 +283,21 @@ assert_gc_unsafe_mode (void)
        case STATE_SELF_SUSPEND_REQUESTED:
                break;
        default:
-               assertion_fail ("Expected GC Unsafe mode but was in %s state", mono_thread_state_name (state));
+               mono_fatal_with_history ("Expected GC Unsafe mode but was in %s state", mono_thread_state_name (state));
        }
 }
 
 void
 assert_gc_neutral_mode (void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        MonoThreadInfo *cur = mono_thread_info_current ();
        int state;
 
        if (!cur)
-               assertion_fail ("Expected GC Neutral mode but thread is not attached");
+               mono_fatal_with_history ("Expected GC Neutral mode but thread is not attached");
 
        switch (state = mono_thread_info_current_state (cur)) {
        case STATE_RUNNING:
@@ -235,13 +307,16 @@ assert_gc_neutral_mode (void)
        case STATE_BLOCKING_AND_SUSPENDED:
                break;
        default:
-               assertion_fail ("Expected GC Neutral mode but was in %s state", mono_thread_state_name (state));
+               mono_fatal_with_history ("Expected GC Neutral mode but was in %s state", mono_thread_state_name (state));
        }
 }
 
 void *
 critical_gc_region_begin(void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return NULL;
+
        CheckState *state = get_state ();
        state->in_gc_critical_region++;
        return state;
@@ -251,6 +326,9 @@ critical_gc_region_begin(void)
 void
 critical_gc_region_end(void* token)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        CheckState *state = get_state();
        g_assert (state == token);
        state->in_gc_critical_region--;
@@ -259,23 +337,29 @@ critical_gc_region_end(void* token)
 void
 assert_not_in_gc_critical_region(void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        CheckState *state = get_state();
        if (state->in_gc_critical_region > 0) {
-               assertion_fail("Expected GC Unsafe mode, but was in %s state", mono_thread_state_name (mono_thread_info_current_state (mono_thread_info_current ())));
+               mono_fatal_with_history("Expected GC Unsafe mode, but was in %s state", mono_thread_state_name (mono_thread_info_current_state (mono_thread_info_current ())));
        }
 }
 
 void
 assert_in_gc_critical_region (void)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_GC))
+               return;
+
        CheckState *state = get_state();
        if (state->in_gc_critical_region == 0)
-               assertion_fail("Expected GC critical region");
+               mono_fatal_with_history("Expected GC critical region");
 }
 
-#endif /* !defined(DISABLE_CHECKED_BUILD_GC) */
+#endif /* defined(ENABLE_CHECKED_BUILD_GC) */
 
-#if !defined(DISABLE_CHECKED_BUILD_METADATA)
+#ifdef ENABLE_CHECKED_BUILD_METADATA
 
 // check_metadata_store et al: The goal of these functions is to verify that if there is a pointer from one mempool into
 // another, that the pointed-to memory is protected by the reference count mechanism for MonoImages.
@@ -543,6 +627,9 @@ mono_find_mempool_owner (void *ptr)
 static void
 check_mempool_may_reference_mempool (void *from_ptr, void *to_ptr, gboolean require_local)
 {
+       if (!mono_check_mode_enabled (MONO_CHECK_MODE_METADATA))
+               return;
+
        // Null pointers are OK
        if (!to_ptr)
                return;
@@ -610,6 +697,6 @@ check_metadata_store_local (void *from, void *to)
     check_mempool_may_reference_mempool (from, to, TRUE);
 }
 
-#endif /* !defined(DISABLE_CHECKED_BUILD_METADATA) */
+#endif /* defined(ENABLE_CHECKED_BUILD_METADATA) */
 
-#endif /* CHECKED_BUILD */
+#endif /* ENABLE_CHECKED_BUILD */
index 28932d8c630204ff83e6bae5d3cd46cb49f2c062..25e663177ef39760a804e16eae34add0147f2f7a 100644 (file)
 
 #include <config.h>
 #include <mono/utils/atomic.h>
+#include <mono/utils/mono-publib.h>
+
+typedef enum {
+       MONO_CHECK_MODE_NONE = 0,
+       MONO_CHECK_MODE_GC = 0x1,
+       MONO_CHECK_MODE_METADATA = 0x2,
+       MONO_CHECK_MODE_THREAD = 0x4,
+       MONO_CHECK_MODE_ALL = MONO_CHECK_MODE_GC | MONO_CHECK_MODE_METADATA | MONO_CHECK_MODE_THREAD,
+       MONO_CHECK_MODE_UNKNOWN = 0x8
+} MonoCheckMode;
+
+mono_bool mono_check_mode_enabled (MonoCheckMode query);
 
 // This is for metadata writes which we have chosen not to check at the current time.
 // Because in principle this should never happen, we still use a macro so that the exemptions will be easier to find, and remove, later.
 // The current reason why this is needed is for pointers to constant strings, which the checker cannot verify yet.
 #define CHECKED_METADATA_WRITE_PTR_EXEMPT(ptr, val) do { (ptr) = (val); } while (0)
 
-#if defined(CHECKED_BUILD)
+#ifdef ENABLE_CHECKED_BUILD
 
 #define g_assert_checked g_assert
 
@@ -45,10 +57,9 @@ void checked_build_init (void);
 
 #define CHECKED_MONO_INIT()
 
-#endif /* CHECKED_BUILD */
-
-#if defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_GC)
+#endif /* ENABLE_CHECKED_BUILD */
 
+#ifdef ENABLE_CHECKED_BUILD_GC
 /*
 GC runtime modes rules:
 
@@ -149,9 +160,9 @@ void assert_in_gc_critical_region (void);
 #define MONO_REQ_GC_NOT_CRITICAL
 #define MONO_REQ_GC_CRITICAL
 
-#endif /* defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_GC) */
+#endif /* defined(ENABLE_CHECKED_BUILD_GC) */
 
-#if defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_METADATA)
+#ifdef ENABLE_CHECKED_BUILD_METADATA
 
 // Use when writing a pointer from one image or imageset to another.
 #define CHECKED_METADATA_WRITE_PTR(ptr, val) do {    \
@@ -180,9 +191,9 @@ void check_metadata_store_local(void *from, void *to);
 #define CHECKED_METADATA_WRITE_PTR_LOCAL(ptr, val) do { (ptr) = (val); } while (0)
 #define CHECKED_METADATA_WRITE_PTR_ATOMIC(ptr, val) do { mono_atomic_store_release (&(ptr), (val)); } while (0)
 
-#endif /* defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_METADATA) */
+#endif /* defined(ENABLE_CHECKED_BUILD_METADATA) */
 
-#if defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_THREAD)
+#ifdef ENABLE_CHECKED_BUILD_THREAD
 
 #define CHECKED_BUILD_THREAD_TRANSITION(transition, info, from_state, suspend_count, next_state, suspend_count_delta) do {     \
        checked_build_thread_transition (transition, info, from_state, suspend_count, next_state, suspend_count_delta); \
@@ -190,10 +201,14 @@ void check_metadata_store_local(void *from, void *to);
 
 void checked_build_thread_transition(const char *transition, void *info, int from_state, int suspend_count, int next_state, int suspend_count_delta);
 
+void mono_fatal_with_history(const char *msg, ...);
+
 #else
 
 #define CHECKED_BUILD_THREAD_TRANSITION(transition, info, from_state, suspend_count, next_state, suspend_count_delta)
 
-#endif /* defined(CHECKED_BUILD) && !defined(DISABLE_CHECKED_BUILD_THREAD) */
+#define mono_fatal_with_history g_error
+
+#endif /* defined(ENABLE_CHECKED_BUILD_THREAD) */
 
 #endif /* __CHECKED_BUILD_H__ */
index 074f947f291ff5be3bec063f56a14989be79c66a..44a8f6b7c7b55abd903984267e19b17bb59bb571 100644 (file)
@@ -52,9 +52,21 @@ extern "C" {
 #define dlindependent_comalloc independent_comalloc
 #endif /* USE_DL_PREFIX */
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/utils/dlmalloc.h"
-#endif
+#define dlcalloc               mono_dlcalloc
+#define dlfree                 mono_dlfree
+#define dlmalloc               mono_dlmalloc
+#define dlmemalign             mono_dlmemalign
+#define dlrealloc              mono_dlrealloc
+#define dlvalloc               mono_dlvalloc
+#define dlpvalloc              mono_dlpvalloc
+#define dlmallinfo             mono_dlmallinfo
+#define dlmallopt              mono_dlmallopt
+#define dlmalloc_trim          mono_dlmalloc_trim
+#define dlmalloc_stats         mono_dlmalloc_stats
+#define dlmalloc_usable_size   mono_dlmalloc_usable_size
+#define dlmalloc_footprint     mono_dlmalloc_footprint
+#define dlindependent_calloc   mono_dlindependent_calloc
+#define dlindependent_comalloc mono_dlindependent_comalloc
 
 /*
   malloc(size_t n)
index a90d27c064f4d60458a09512fc5cdf32ef8a9b82..908bcabc5125d0e594237ac67286015302cd8ff9 100644 (file)
@@ -1,6 +1,7 @@
 /* 
  * Copyright 2004-2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_OS_GC_WRAPPER_H__
 #define __MONO_OS_GC_WRAPPER_H__
index df1e4cdc8e96744b8aed11c16686b66af0064fdd..efe6b649b3039450cbdc176f0373cd55754a69be 100644 (file)
@@ -2,6 +2,7 @@
  * hazard-pointer.c: Hazard pointer related code.
  *
  * (C) Copyright 2011 Novell, Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -42,6 +43,7 @@ typedef struct {
 
 static volatile int hazard_table_size = 0;
 static MonoThreadHazardPointers * volatile hazard_table = NULL;
+static MonoHazardFreeQueueSizeCallback queue_size_cb;
 
 /*
  * Each entry is either 0 or 1, indicating whether that overflow small
@@ -305,29 +307,63 @@ try_free_delayed_free_item (HazardFreeContext context)
        return TRUE;
 }
 
+/**
+ * mono_thread_hazardous_try_free:
+ * @p: the pointer to free
+ * @free_func: the function that can free the pointer
+ *
+ * If @p is not a hazardous pointer it will be immediately freed by calling @free_func.
+ * Otherwise it will be queued for later.
+ *
+ * Use this function if @free_func can ALWAYS be called in the context where this function is being called.
+ *
+ * This function doesn't pump the free queue so try to accommodate a call at an appropriate time.
+ * See mono_thread_hazardous_try_free_some for when it's appropriate.
+ *
+ * Return: TRUE if @p was free or FALSE if it was queued.
+ */
+gboolean
+mono_thread_hazardous_try_free (gpointer p, MonoHazardousFreeFunc free_func)
+{
+       if (!is_pointer_hazardous (p)) {
+               free_func (p);
+               return TRUE;
+       } else {
+               mono_thread_hazardous_queue_free (p, free_func);
+               return FALSE;
+       }
+}
+
+/**
+ * mono_thread_hazardous_queue_free:
+ * @p: the pointer to free
+ * @free_func: the function that can free the pointer
+ *
+ * Queue @p to be freed later. @p will be freed once the hazard free queue is pumped.
+ *
+ * This function doesn't pump the free queue so try to accommodate a call at an appropriate time.
+ * See mono_thread_hazardous_try_free_some for when it's appropriate.
+ *
+ */
 void
-mono_thread_hazardous_free_or_queue (gpointer p, MonoHazardousFreeFunc free_func,
-                                     HazardFreeLocking locking, HazardFreeContext context)
+mono_thread_hazardous_queue_free (gpointer p, MonoHazardousFreeFunc free_func)
 {
-       int i;
+       DelayedFreeItem item = { p, free_func, HAZARD_FREE_MAY_LOCK };
 
-       /* First try to free a few entries in the delayed free
-          table. */
-       for (i = 0; i < 3; ++i)
-               try_free_delayed_free_item (context);
+       InterlockedIncrement (&hazardous_pointer_count);
 
-       /* Now see if the pointer we're freeing is hazardous.  If it
-          isn't, free it.  Otherwise put it in the delay list. */
-       if ((context == HAZARD_FREE_ASYNC_CTX && locking == HAZARD_FREE_MAY_LOCK) ||
-           is_pointer_hazardous (p)) {
-               DelayedFreeItem item = { p, free_func, locking };
+       mono_lock_free_array_queue_push (&delayed_free_queue, &item);
 
-               ++hazardous_pointer_count;
+       guint32 queue_size = delayed_free_queue.num_used_entries;
+       if (queue_size && queue_size_cb)
+               queue_size_cb (queue_size);
+}
 
-               mono_lock_free_array_queue_push (&delayed_free_queue, &item);
-       } else {
-               free_func (p);
-       }
+
+void
+mono_hazard_pointer_install_free_queue_size_callback (MonoHazardFreeQueueSizeCallback cb)
+{
+       queue_size_cb = cb;
 }
 
 void
index fa70e71bb40d1853f0269b95ada6d32f1262eda7..0102c103f7629785b1eb8c231a88f86269dbc56c 100644 (file)
@@ -2,6 +2,7 @@
  * hazard-pointer.h: Hazard pointer related code.
  *
  * (C) Copyright 2011 Novell, Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_HAZARD_POINTER_H__
 #define __MONO_HAZARD_POINTER_H__
@@ -9,6 +10,7 @@
 #include <glib.h>
 #include <mono/utils/mono-compiler.h>
 #include <mono/utils/mono-membar.h>
+#include <mono/utils/mono-publib.h>
 
 #define HAZARD_POINTER_COUNT 3
 
@@ -28,8 +30,9 @@ typedef enum {
        HAZARD_FREE_ASYNC_CTX,
 } HazardFreeContext;
 
-void mono_thread_hazardous_free_or_queue (gpointer p, MonoHazardousFreeFunc free_func,
-                                          HazardFreeLocking locking, HazardFreeContext context);
+MONO_API gboolean mono_thread_hazardous_try_free (gpointer p, MonoHazardousFreeFunc free_func);
+void mono_thread_hazardous_queue_free (gpointer p, MonoHazardousFreeFunc free_func);
+
 void mono_thread_hazardous_try_free_all (void);
 void mono_thread_hazardous_try_free_some (void);
 MonoThreadHazardPointers* mono_hazard_pointer_get (void);
@@ -57,6 +60,9 @@ int mono_thread_small_id_alloc (void);
 int mono_hazard_pointer_save_for_signal_handler (void);
 void mono_hazard_pointer_restore_for_signal_handler (int small_id);
 
+typedef void (*MonoHazardFreeQueueSizeCallback)(size_t size);
+void mono_hazard_pointer_install_free_queue_size_callback (MonoHazardFreeQueueSizeCallback cb);
+
 void mono_thread_smr_init (void);
 void mono_thread_smr_cleanup (void);
 #endif /*__MONO_HAZARD_POINTER_H__*/
index 2ca9ec247457aa5490ec14587282698366ab081c..331f9038081e178c45067a123ccedf5e4e9c9c01 100644 (file)
@@ -5,6 +5,7 @@
  *   Joao Matos (joao.matos@xamarin.com)
  *
  * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <mono/utils/json.h>
index cee9c8905dcfa9ea200a8bc63b07b11037a35c8e..79b26165e77eb3a7c6518733c60a89e881b028f3 100644 (file)
@@ -5,6 +5,7 @@
  *   Joao Matos (joao.matos@xamarin.com)
  *
  * Copyright 2015 Xamarin Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_UTILS_JSON_H__
index 66cb6ea3f8075fc44c9e6793c6bb86b5a7350844..3be8342a49873dbc9e2796d44a76a81d5a9302e3 100644 (file)
@@ -3,24 +3,7 @@
  *
  * (C) Copyright 2011 Novell, Inc
  *
- * Permission is hereby granted, free of charge, to any person obtaining
- * a copy of this software and associated documentation files (the
- * "Software"), to deal in the Software without restriction, including
- * without limitation the rights to use, copy, modify, merge, publish,
- * distribute, sublicense, and/or sell copies of the Software, and to
- * permit persons to whom the Software is furnished to do so, subject to
- * the following conditions:
- * 
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- * 
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
- * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
- * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
- * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
- * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
@@ -250,7 +233,7 @@ desc_retire (Descriptor *desc)
        g_assert (desc->in_use);
        desc->in_use = FALSE;
        free_sb (desc->sb, desc->block_size);
-       mono_thread_hazardous_free_or_queue (desc, desc_enqueue_avail, HAZARD_FREE_NO_LOCK, HAZARD_FREE_ASYNC_CTX);
+       mono_thread_hazardous_try_free (desc, desc_enqueue_avail);
 }
 #else
 MonoLockFreeQueue available_descs;
@@ -294,7 +277,7 @@ desc_put_partial (gpointer _desc)
 
        g_assert (desc->anchor.data.state != STATE_FULL);
 
-       mono_lock_free_queue_node_free (&desc->node);
+       mono_lock_free_queue_node_unpoison (&desc->node);
        mono_lock_free_queue_enqueue (&desc->heap->sc->partial, &desc->node);
 }
 
@@ -302,7 +285,7 @@ static void
 list_put_partial (Descriptor *desc)
 {
        g_assert (desc->anchor.data.state != STATE_FULL);
-       mono_thread_hazardous_free_or_queue (desc, desc_put_partial, HAZARD_FREE_NO_LOCK, HAZARD_FREE_ASYNC_CTX);
+       mono_thread_hazardous_try_free (desc, desc_put_partial);
 }
 
 static void
@@ -321,7 +304,7 @@ list_remove_empty_desc (MonoLockFreeAllocSizeClass *sc)
                        desc_retire (desc);
                } else {
                        g_assert (desc->heap->sc == sc);
-                       mono_thread_hazardous_free_or_queue (desc, desc_put_partial, HAZARD_FREE_NO_LOCK, HAZARD_FREE_ASYNC_CTX);
+                       mono_thread_hazardous_try_free (desc, desc_put_partial);
                        if (++num_non_empty >= 2)
                                return;
                }
index 9cbfdec5e9955a1cea60a1960b3d8473ddaf5167..f0420b492ec1bc39ee043f826f85bd933996ea0f 100644 (file)
@@ -47,12 +47,12 @@ typedef struct {
 #define LOCK_FREE_ALLOC_SB_HEADER_SIZE                         (sizeof (MonoLockFreeAllocator))
 #define LOCK_FREE_ALLOC_SB_USABLE_SIZE(block_size)     ((block_size) - LOCK_FREE_ALLOC_SB_HEADER_SIZE)
 
-void mono_lock_free_allocator_init_size_class (MonoLockFreeAllocSizeClass *sc, unsigned int slot_size, unsigned int block_size);
-void mono_lock_free_allocator_init_allocator (MonoLockFreeAllocator *heap, MonoLockFreeAllocSizeClass *sc);
+MONO_API void mono_lock_free_allocator_init_size_class (MonoLockFreeAllocSizeClass *sc, unsigned int slot_size, unsigned int block_size);
+MONO_API void mono_lock_free_allocator_init_allocator (MonoLockFreeAllocator *heap, MonoLockFreeAllocSizeClass *sc);
 
-gpointer mono_lock_free_alloc (MonoLockFreeAllocator *heap);
-void mono_lock_free_free (gpointer ptr, size_t block_size);
+MONO_API gpointer mono_lock_free_alloc (MonoLockFreeAllocator *heap);
+MONO_API void mono_lock_free_free (gpointer ptr, size_t block_size);
 
-gboolean mono_lock_free_allocator_check_consistency (MonoLockFreeAllocator *heap);
+MONO_API gboolean mono_lock_free_allocator_check_consistency (MonoLockFreeAllocator *heap);
 
 #endif
index 98a3f31745a67bbc88d0a21ceae14c29d3b3b365..b0d0a9a1dfe593ab67005f1cb52e960b0d89447b 100644 (file)
@@ -3,6 +3,7 @@
  * require hazard pointers.
  *
  * (C) Copyright 2011 Xamarin Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index 620025153deeebfcb687463b8694e3a85f37201b..fc924a7639ab011bf567d6f44db039d9648ee899 100644 (file)
@@ -3,6 +3,7 @@
  * require hazard pointers.
  *
  * (C) Copyright 2011 Xamarin Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_LOCK_FREE_ARRAY_QUEUE_H__
 #define __MONO_LOCK_FREE_ARRAY_QUEUE_H__
index b0076c6d18441ade1e6d345282b60652a5f3c57e..2e06b63f526258de4e6f2004e3fd397d8f523611 100644 (file)
@@ -61,6 +61,9 @@
 #define END_MARKER     ((MonoLockFreeQueueNode *volatile)-2)
 #define FREE_NEXT      ((MonoLockFreeQueueNode *volatile)-3)
 
+/*
+ * Initialize a lock-free queue in-place at @q.
+ */
 void
 mono_lock_free_queue_init (MonoLockFreeQueue *q)
 {
@@ -77,17 +80,30 @@ mono_lock_free_queue_init (MonoLockFreeQueue *q)
        q->has_dummy = 1;
 }
 
+/*
+ * Initialize @node's state. If @poison is TRUE, @node may not be enqueued to a
+ * queue - @mono_lock_free_queue_node_unpoison must be called first; otherwise,
+ * the node can be enqueued right away.
+ *
+ * The poisoning feature is mainly intended for ensuring correctness in complex
+ * lock-free code that uses the queue. For example, in some code that reuses
+ * nodes, nodes can be poisoned when they're dequeued, and then unpoisoned and
+ * enqueued in their hazard free callback.
+ */
 void
-mono_lock_free_queue_node_init (MonoLockFreeQueueNode *node, gboolean to_be_freed)
+mono_lock_free_queue_node_init (MonoLockFreeQueueNode *node, gboolean poison)
 {
-       node->next = to_be_freed ? INVALID_NEXT : FREE_NEXT;
+       node->next = poison ? INVALID_NEXT : FREE_NEXT;
 #ifdef QUEUE_DEBUG
        node->in_queue = FALSE;
 #endif
 }
 
+/*
+ * Unpoisons @node so that it may be enqueued.
+ */
 void
-mono_lock_free_queue_node_free (MonoLockFreeQueueNode *node)
+mono_lock_free_queue_node_unpoison (MonoLockFreeQueueNode *node)
 {
        g_assert (node->next == INVALID_NEXT);
 #ifdef QUEUE_DEBUG
@@ -96,6 +112,10 @@ mono_lock_free_queue_node_free (MonoLockFreeQueueNode *node)
        node->next = FREE_NEXT;
 }
 
+/*
+ * Enqueue @node to @q. @node must have been initialized by a prior call to
+ * @mono_lock_free_queue_node_init, and must not be in a poisoned state.
+ */
 void
 mono_lock_free_queue_enqueue (MonoLockFreeQueue *q, MonoLockFreeQueueNode *node)
 {
@@ -158,7 +178,7 @@ static void
 free_dummy (gpointer _dummy)
 {
        MonoLockFreeQueueDummy *dummy = (MonoLockFreeQueueDummy *) _dummy;
-       mono_lock_free_queue_node_free (&dummy->node);
+       mono_lock_free_queue_node_unpoison (&dummy->node);
        g_assert (dummy->in_use);
        mono_memory_write_barrier ();
        dummy->in_use = 0;
@@ -183,7 +203,7 @@ get_dummy (MonoLockFreeQueue *q)
 static gboolean
 is_dummy (MonoLockFreeQueue *q, MonoLockFreeQueueNode *n)
 {
-       return n >= &q->dummies [0].node && n < &q->dummies [MONO_LOCK_FREE_QUEUE_NUM_DUMMIES].node;
+       return n >= &q->dummies [0].node && n <= &q->dummies [MONO_LOCK_FREE_QUEUE_NUM_DUMMIES-1].node;
 }
 
 static gboolean
@@ -208,6 +228,11 @@ try_reenqueue_dummy (MonoLockFreeQueue *q)
        return TRUE;
 }
 
+/*
+ * Dequeues a node from @q. Returns NULL if no nodes are available. The returned
+ * node is hazardous and must be freed with @mono_thread_hazardous_try_free or
+ * @mono_thread_hazardous_queue_free - it must not be freed directly.
+ */
 MonoLockFreeQueueNode*
 mono_lock_free_queue_dequeue (MonoLockFreeQueue *q)
 {
@@ -286,7 +311,7 @@ mono_lock_free_queue_dequeue (MonoLockFreeQueue *q)
                g_assert (q->has_dummy);
                q->has_dummy = 0;
                mono_memory_write_barrier ();
-               mono_thread_hazardous_free_or_queue (head, free_dummy, HAZARD_FREE_NO_LOCK, HAZARD_FREE_ASYNC_CTX);
+               mono_thread_hazardous_try_free (head, free_dummy);
                if (try_reenqueue_dummy (q))
                        goto retry;
                return NULL;
index 6ae52471e5b4967467b88eb319fabf67944216f9..300b4556ef251f3fb64274a8a4fe7c0d6d592059 100644 (file)
@@ -58,8 +58,8 @@ typedef struct {
 
 MONO_API void mono_lock_free_queue_init (MonoLockFreeQueue *q);
 
-MONO_API void mono_lock_free_queue_node_init (MonoLockFreeQueueNode *node, gboolean to_be_freed);
-MONO_API void mono_lock_free_queue_node_free (MonoLockFreeQueueNode *node);
+MONO_API void mono_lock_free_queue_node_init (MonoLockFreeQueueNode *node, gboolean poison);
+MONO_API void mono_lock_free_queue_node_unpoison (MonoLockFreeQueueNode *node);
 
 MONO_API void mono_lock_free_queue_enqueue (MonoLockFreeQueue *q, MonoLockFreeQueueNode *node);
 
index 19e745f630c0c54eb46f030dfb5c3e62e7b7de20..314b30d972c2b18c065f33f6978a050b64bb10f0 100644 (file)
@@ -27,7 +27,7 @@ mono_mach_get_threads (thread_act_array_t *threads, guint32 *count)
 
        do {
                ret = task_threads (current_task (), threads, count);
-       } while (ret != KERN_SUCCESS);
+       } while (ret == KERN_ABORTED);
 
        return ret;
 }
index f657b5532ee76999e868360a7dbc69f3e5fe4b0b..455ffe77ea44acc865935bab96f757e0114e71b4 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2013-2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 /*
index 51a3618e70640d87cd09046f6b6910b6db130a0e..24cc0544474044307cc06261b69a2d0bf3ba59cf 100644 (file)
@@ -3,18 +3,8 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_UTILS_MEMFUNCS_H__
index 2b3b86e2ef2e305dd8de427b6eb4902b999283de..04bc26e4f53ff3ef3796dc25ba3536144b6ba48d 100644 (file)
@@ -7,6 +7,19 @@
  */
 #include <config.h>
 
+/*
+ * When embedding, you have to define MONO_ZERO_LEN_ARRAY before including any
+ * other Mono header file if you use a different compiler from the one used to
+ * build Mono.
+ */
+#ifndef MONO_ZERO_LEN_ARRAY
+#ifdef __GNUC__
+#define MONO_ZERO_LEN_ARRAY 0
+#else
+#define MONO_ZERO_LEN_ARRAY 1
+#endif
+#endif
+
 #ifdef __GNUC__
 #define MONO_ATTR_USED __attribute__ ((used))
 #else
index 798fddb263b00c2081b43b6e14f066fe2b84dcf6..af13bf62b982d00032f425312560f2312d5a505a 100644 (file)
@@ -5,6 +5,7 @@
 *      Joao Matos (joao.matos@xamarin.com)
 *
 * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+* Licensed under the MIT license. See LICENSE file in the project root for full license information.
 */
 
 #include <config.h>
index 58cf945facf0a0136f920c2f94d72622df4c7ea9..b5b3539d116c00eef3eba67d112ff9d521df3f9c 100644 (file)
@@ -56,7 +56,7 @@ conc_table_free (gpointer ptr)
 static void
 conc_table_lf_free (conc_table *table)
 {
-       mono_thread_hazardous_free_or_queue (table, conc_table_free, HAZARD_FREE_MAY_LOCK, HAZARD_FREE_SAFE_CTX);
+       mono_thread_hazardous_try_free (table, conc_table_free);
 }
 
 
index 81aff561ccab6650b420e92d2613a423e519b243..632513d874f7c8069bd6a1ee0d57c23b1c06bdd3 100644 (file)
@@ -3,6 +3,7 @@
  *
  *
  * Copyright (c) 2011 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <mono/utils/mono-sigcontext.h>
index 2661e657636dde188bb897b51a5284f77f254c3f..374171cf6747b828f5e85b5e649cc07fd08a6a8e 100644 (file)
@@ -3,6 +3,7 @@
  *
  *
  * Copyright (c) 2011 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 
@@ -30,7 +31,7 @@
 /*HACK, move this to an eventual mono-signal.c*/
 #if defined( __linux__) || defined(__sun) || defined(__APPLE__) || defined(__NetBSD__) || \
        defined(__FreeBSD__) || defined(__OpenBSD__)
-#ifdef HAVE_SIGACTION
+#if defined(HAVE_SIGACTION) || defined(__APPLE__)  // the __APPLE__ check is required for the tvos simulator, which has ucontext_t but not sigaction
 #define MONO_SIGNAL_USE_UCONTEXT_T 1
 #endif
 #endif
@@ -151,7 +152,7 @@ typedef struct {
 
 #if !defined( HOST_WIN32 ) && !defined(__native_client__) && !defined(__native_client_codegen__)
 
-#ifdef HAVE_SIGACTION
+#if defined(HAVE_SIGACTION) || defined(__APPLE__)  // the __APPLE__ check is required for the tvos simulator, which has ucontext_t but not sigaction
 #define MONO_SIGNAL_USE_UCONTEXT_T 1
 #endif
 
index 17170a40ed2bec07c33b774255203416740f5543..2ca19a8b3d645fca66230e58f15d4b0e2b9cccf2 100644 (file)
@@ -1,6 +1,7 @@
 /*
  * Copyright 2006-2010 Novell
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <stdlib.h>
@@ -560,7 +561,7 @@ dump_counter (MonoCounter *counter, FILE *outfile) {
 }
 
 static const char
-section_names [][10] = {
+section_names [][12] = {
        "JIT",
        "GC",
        "Metadata",
@@ -568,6 +569,8 @@ section_names [][10] = {
        "Security",
        "Runtime",
        "System",
+       "", // MONO_COUNTER_PERFCOUNTERS - not used.
+       "Profiler",
 };
 
 static void
index a8e6928dfbe84d036be48f0ef52e79987a24a97c..20be122e58288ccbd62cdcb25ab464080e9604d1 100644 (file)
@@ -26,6 +26,7 @@ enum {
        MONO_COUNTER_RUNTIME  = 1 << 13,
        MONO_COUNTER_SYSTEM   = 1 << 14,
        MONO_COUNTER_PERFCOUNTERS = 1 << 15,
+       MONO_COUNTER_PROFILER = 1 << 16,
        MONO_COUNTER_LAST_SECTION,
 
        /* Unit, bits 24-27 (4 bits) */
index ff7028555c18d05f5a310a58a5caa2739e7cd4c0..225706c547ac78f411d6a57bc554f8e29e7d5290 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2004 Ximian, Inc.
  * Copyright 2004-2009 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 
index 97b13c6c189b5d4707234e5de28797e82228b016..6e4b81eaf791a12b6c2191d1a767a1bbb0d29957 100644 (file)
@@ -6,6 +6,7 @@
 MONO_BEGIN_DECLS
 
 enum {
+       MONO_DL_EAGER = 0,
        MONO_DL_LAZY  = 1,
        MONO_DL_LOCAL = 2,
        MONO_DL_MASK  = 3
index 09eed6222e2ff55103654335c72eed343cca79a1..b48a1831d757df85fc1f2f9c1f6756f91cba9695 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2004 Ximian, Inc.
  * Copyright 2004-2009 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 
index 19ff818f733af5e40e54a74347a51b75a2a92201..9e3efa796f7aa93503ab2fa1712d2be476519c73 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2004 Ximian, Inc.
  * Copyright 2004-2009 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <config.h>
 
index aa57e04a50ec92185fc5d54a045e518f4be98458..43116130309eec7195e24a87f8d39e10e544dbce 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2001-2004 Ximian, Inc.
  * Copyright 2004-2009 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 #include "mono/utils/mono-dl.h"
@@ -401,28 +402,35 @@ mono_dl_open_runtime_lib (const char* lib_name, int flags, char **error_msg)
        if (binl != -1) {
                char *base;
                char *resolvedname, *name;
+               char *baseparent = NULL;
                buf [binl] = 0;
                resolvedname = mono_path_resolve_symlinks (buf);
                base = g_path_get_dirname (resolvedname);
                name = g_strdup_printf ("%s/.libs", base);
                runtime_lib = try_load (lib_name, name, flags, error_msg);
                g_free (name);
+               if (!runtime_lib)
+                       baseparent = g_path_get_dirname (base);
                if (!runtime_lib) {
-                       char *newbase = g_path_get_dirname (base);
-                       name = g_strdup_printf ("%s/lib", newbase);
+                       name = g_strdup_printf ("%s/lib", baseparent);
                        runtime_lib = try_load (lib_name, name, flags, error_msg);
                        g_free (name);
                }
 #ifdef __MACH__
                if (!runtime_lib) {
-                       char *newbase = g_path_get_dirname (base);
-                       name = g_strdup_printf ("%s/Libraries", newbase);
+                       name = g_strdup_printf ("%s/Libraries", baseparent);
                        runtime_lib = try_load (lib_name, name, flags, error_msg);
                        g_free (name);
                }
 #endif
+               if (!runtime_lib) {
+                       name = g_strdup_printf ("%s/profiler/.libs", baseparent);
+                       runtime_lib = try_load (lib_name, name, flags, error_msg);
+                       g_free (name);
+               }
                g_free (base);
                g_free (resolvedname);
+               g_free (baseparent);
        }
        if (!runtime_lib)
                runtime_lib = try_load (lib_name, NULL, flags, error_msg);
index 3bb1ac6bff637b4e8e0c60396dc382786c502dbc..de78a84aa431f0e84026576401ba4acdac96e84d 100644 (file)
@@ -10,6 +10,7 @@
  * Copyright 2001-2004 Ximian, Inc.
  * Copyright 2004-2010 Novell, Inc.
  *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include "config.h"
 #include "mono/utils/mono-dl.h"
index 8fb01856673ecca132b5ab4eee9353a299190322..63607a8fb89eb962ba99887b2941a5963cd6a7ed 100644 (file)
@@ -2,7 +2,7 @@
 #define __MONO_ERROR_INTERNALS_H__
 
 #include "mono/utils/mono-compiler.h"
-#include "mono/metadata/object-internals.h"
+#include "mono/metadata/class-internals.h"
 
 /*Keep in sync with MonoError*/
 typedef struct {
@@ -42,6 +42,11 @@ typedef struct {
 #define return_if_nok(error) do { if (!is_ok ((error))) return; } while (0)
 #define return_val_if_nok(error,val) do { if (!is_ok ((error))) return (val); } while (0)
 
+/* Only use this in icalls */
+#define return_val_and_set_pending_if_nok(error,value) \
+       if (mono_error_set_pending_exception ((error))) \
+               return (value);
+
 void
 mono_error_assert_ok_pos (MonoError *error, const char* filename, int lineno) MONO_LLVM_INTERNAL;
 
@@ -94,10 +99,19 @@ void
 mono_error_set_generic_error (MonoError *error, const char * name_space, const char *name, const char *msg_format, ...);
 
 void
-mono_error_set_exception_instance (MonoError *error, MonoException *exc);
+mono_error_set_execution_engine (MonoError *error, const char *msg_format, ...);
+
+void
+mono_error_set_not_implemented (MonoError *error, const char *msg_format, ...);
+
+void
+mono_error_set_not_supported (MonoError *error, const char *msg_format, ...);
 
 void
-mono_error_set_from_loader_error (MonoError *error);
+mono_error_set_invalid_operation (MonoError *error, const char *msg_format, ...);
+
+void
+mono_error_set_exception_instance (MonoError *error, MonoException *exc);
 
 MonoException*
 mono_error_prepare_exception (MonoError *error, MonoError *error_out);
@@ -108,9 +122,6 @@ mono_error_convert_to_exception (MonoError *error);
 void
 mono_error_raise_exception (MonoError *error);
 
-void
-mono_loader_set_error_from_mono_error (MonoError *oerror);
-
 void
 mono_error_move (MonoError *dest, MonoError *src);
 
index b6f2ee0979524b82e12815c5bd57731c7d1886a4..84d04781e708927500ec5fc106ec46066cacfda4 100644 (file)
@@ -4,6 +4,7 @@
  * Authors:
  *     Rodrigo Kumpera    (rkumpera@novell.com)
  * Copyright 2009 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #include <glib.h>
 
 #include "mono-error-internals.h"
 
 #include <mono/metadata/exception.h>
-#include <mono/metadata/class-internals.h>
 #include <mono/metadata/debug-helpers.h>
-#include <mono/metadata/object.h>
 #include <mono/metadata/object-internals.h>
 
+#define set_error_messagev() do { \
+       if (!(error->full_message = g_strdup_vprintf (msg_format, args))) \
+                       error->flags |= MONO_ERROR_INCOMPLETE; \
+} while (0)
+
 #define set_error_message() do { \
        va_list args; \
        va_start (args, msg_format); \
-       if (!(error->full_message = g_strdup_vprintf (msg_format, args))) \
-                       error->flags |= MONO_ERROR_INCOMPLETE; \
+       set_error_messagev();        \
        va_end (args); \
 } while (0)
 
+static void
+mono_error_set_generic_errorv (MonoError *oerror, const char *name_space, const char *name, const char *msg_format, va_list args);
+
 static gboolean
 is_managed_exception (MonoErrorInternal *error)
 {
@@ -83,6 +89,13 @@ mono_error_init_flags (MonoError *oerror, unsigned short flags)
        error->flags = flags;
 }
 
+/**
+ * mono_error_init:
+ * @error: Pointer to MonoError struct to initialize
+ *
+ * Any function which takes a MonoError for purposes of reporting an error
+ * is required to call either this or mono_error_init_flags on entry.
+ */
 void
 mono_error_init (MonoError *error)
 {
@@ -332,130 +345,89 @@ mono_error_set_bad_image (MonoError *oerror, MonoImage *image, const char *msg_f
 }
 
 void
-mono_error_set_generic_error (MonoError *oerror, const char * name_space, const char *name, const char *msg_format, ...)
+mono_error_set_generic_errorv (MonoError *oerror, const char *name_space, const char *name, const char *msg_format, va_list args)
 {
        MonoErrorInternal *error = (MonoErrorInternal*)oerror;
        mono_error_prepare (error);
 
        error->error_code = MONO_ERROR_GENERIC;
        mono_error_set_corlib_exception (oerror, name_space, name);
-       set_error_message ();
+       set_error_messagev ();
 }
 
 void
-mono_error_set_exception_instance (MonoError *oerror, MonoException *exc)
+mono_error_set_generic_error (MonoError *oerror, const char * name_space, const char *name, const char *msg_format, ...)
 {
-       MonoErrorInternal *error = (MonoErrorInternal*)oerror;
-
-       mono_error_prepare (error);
-       error->error_code = MONO_ERROR_EXCEPTION_INSTANCE;
-       error->exn.instance_handle = mono_gchandle_new (exc ? &exc->object : NULL, FALSE);
+       va_list args;
+       va_start (args, msg_format);
+       mono_error_set_generic_errorv (oerror, name_space, name, msg_format, args);
+       va_end (args);
 }
 
+/**
+ * mono_error_set_not_implemented:
+ *
+ * System.NotImplementedException
+ */
 void
-mono_error_set_from_loader_error (MonoError *oerror)
+mono_error_set_not_implemented (MonoError *oerror, const char *msg_format, ...)
 {
-       MonoLoaderError *loader_error = mono_loader_get_last_error ();
-       MonoErrorInternal *error = (MonoErrorInternal*)oerror;
-       gboolean dup_strings = TRUE;
-
-       mono_error_prepare (error);
-
-       if (!loader_error) {
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Runtime tried to produce a mono-error from an empty loader-error");
-               return;
-       }
-
-       switch (loader_error->exception_type) {
-       case MONO_EXCEPTION_NONE:
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Runtime tried to produce a mono-error from a non-error loader-error");
-               break;
-
-       case MONO_EXCEPTION_INVALID_PROGRAM:
-               mono_error_set_generic_error (oerror, "System", "InvalidProgramException", "Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_UNVERIFIABLE_IL:
-               mono_error_set_generic_error (oerror, "System.Security", "VerificationException", "Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_MISSING_METHOD:
-               error->error_code = MONO_ERROR_MISSING_METHOD;
-               mono_error_set_type_name (oerror, loader_error->class_name);
-               mono_error_set_member_name (oerror, loader_error->member_name);
-               error->full_message = g_strdup ("Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_MISSING_FIELD:
-               mono_error_set_field_load (oerror, loader_error->klass, loader_error->member_name, "Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_TYPE_LOAD:
-               mono_error_set_type_load_name (oerror, g_strdup (loader_error->class_name), g_strdup (loader_error->assembly_name), "Failed for unknown reasons.");
-               dup_strings = FALSE;
-               break;
-       
-       case MONO_EXCEPTION_FILE_NOT_FOUND:
-               mono_error_set_assembly_load_simple (oerror, loader_error->assembly_name, loader_error->ref_only);
-               break;
-
-       case MONO_EXCEPTION_METHOD_ACCESS:
-               mono_error_set_generic_error (oerror, "System", "MethodAccessException", "Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_FIELD_ACCESS:
-               mono_error_set_generic_error (oerror, "System", "FieldAccessException", "Failed for unknown reasons.");
-               break;
-
-       case MONO_EXCEPTION_OBJECT_SUPPLIED:
-       case MONO_EXCEPTION_GENERIC_SHARING_FAILED:
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Runtime tried to produce a mono-error from JIT internal error %d", loader_error->exception_type);
-               break;
-
-       case MONO_EXCEPTION_BAD_IMAGE:
-               mono_error_set_bad_image_name (oerror, "<unknown>", "%s", loader_error->msg);
-               break;
+       va_list args;
+       va_start (args, msg_format);
+       mono_error_set_generic_errorv (oerror, "System", "NotImplementedException", msg_format, args);
+       va_end (args);
+}
 
-       case MONO_EXCEPTION_OUT_OF_MEMORY:
-               mono_error_set_out_of_memory (oerror, "Failed for unknown reasons.");
-               break;
+/**
+ * mono_error_set_execution_engine:
+ *
+ * System.ExecutionEngineException
+ */
+void
+mono_error_set_execution_engine (MonoError *oerror, const char *msg_format, ...)
+{
+       va_list args;
+       va_start (args, msg_format);
+       mono_error_set_generic_errorv (oerror, "System", "ExecutionEngineException", msg_format, args);
+       va_end (args);
+}
 
-       default:
-               mono_error_set_generic_error (oerror, "System", "ExecutionEngineException", "Runtime tried to produce an unknown loader-error %d", loader_error->exception_type);
-               break;
-       }
+/**
+ * mono_error_set_not_supported:
+ *
+ * System.NotSupportedException
+ */
+void
+mono_error_set_not_supported (MonoError *oerror, const char *msg_format, ...)
+{
+       va_list args;
+       va_start (args, msg_format);
+       mono_error_set_generic_errorv (oerror, "System", "NotSupportedException", msg_format, args);
+       va_end (args);
+}
 
-       mono_error_dup_strings (oerror, dup_strings);
-       mono_loader_clear_error ();
+/**
+ * mono_error_set_invalid_operation:
+ *
+ * System.InvalidOperationException
+ */
+void
+mono_error_set_invalid_operation (MonoError *oerror, const char *msg_format, ...)
+{
+       va_list args;
+       va_start (args, msg_format);
+       mono_error_set_generic_errorv (oerror, "System", "InvalidOperationException", msg_format, args);
+       va_end (args);
 }
 
 void
-mono_loader_set_error_from_mono_error (MonoError *oerror)
+mono_error_set_exception_instance (MonoError *oerror, MonoException *exc)
 {
        MonoErrorInternal *error = (MonoErrorInternal*)oerror;
 
-       switch (error->error_code) {
-       case MONO_ERROR_MISSING_METHOD:
-               mono_loader_set_error_method_load (get_type_name (error), error->member_name);
-               break;
-       case MONO_ERROR_MISSING_FIELD:
-               mono_loader_set_error_field_load (error->exn.klass, error->member_name);
-               break;
-       case MONO_ERROR_TYPE_LOAD:
-               mono_loader_set_error_type_load (get_type_name (error), get_assembly_name (error));
-               break;
-       case MONO_ERROR_FILE_NOT_FOUND:
-               /* XXX can't recover if it's ref only or not */
-               mono_loader_set_error_assembly_load (get_assembly_name (error), FALSE);
-               break;
-       case MONO_ERROR_BAD_IMAGE:
-               mono_loader_set_error_bad_image (g_strdup (error->full_message));
-               break;
-       case MONO_ERROR_EXCEPTION_INSTANCE:
-               mono_loader_set_error_bad_image (g_strdup_printf ("Non translatable error"));
-       default:
-               mono_loader_set_error_bad_image (g_strdup_printf ("Non translatable error: %s", error->full_message));
-       }
+       mono_error_prepare (error);
+       error->error_code = MONO_ERROR_EXCEPTION_INSTANCE;
+       error->exn.instance_handle = mono_gchandle_new (exc ? &exc->object : NULL, FALSE);
 }
 
 void
@@ -683,7 +655,7 @@ mono_error_prepare_exception (MonoError *oerror, MonoError *error_out)
        }
        case MONO_ERROR_GENERIC:
                if (!error->exception_name_space || !error->exception_name)
-                       mono_error_set_generic_error (error_out, "System", "ExecutionEngineException", "MonoError with generic error but no exception name was supplied");
+                       mono_error_set_execution_engine (error_out, "MonoError with generic error but no exception name was supplied");
                else
                        exception = mono_exception_from_name_msg (mono_defaults.corlib, error->exception_name_space, error->exception_name, error->full_message);
                break;
@@ -693,7 +665,7 @@ mono_error_prepare_exception (MonoError *oerror, MonoError *error_out)
                break;
 
        default:
-               mono_error_set_generic_error (error_out, "System", "ExecutionEngineException", "Invalid error-code %d", error->error_code);
+               mono_error_set_execution_engine (error_out, "Invalid error-code %d", error->error_code);
        }
 
        if (!mono_error_ok (error_out))
index c559ad3185dddd98572144b757fe31e93459db52..cd93eaff39fc9aacdee597c3a2d69c2c5b9fded6 100644 (file)
@@ -5,6 +5,7 @@
  *   Paolo Molaro (lupus@ximian.com)
  *
  * Copyright 2008-2008 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 2df530d824e4e7759288e2c089ab942e1cb681da..6cf8065d06a43e421bfb59737800ff73536d3f86 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-arm.h"
index 5149cc06943c4b6dfc118dc874a29014b7f82341..5491cff96cfd60ec93560dee66aa7343c11c5803 100644 (file)
@@ -2,6 +2,7 @@
  * mono-hwcap-arm64.c: ARM hardware feature detection
  *
  * Copyright 2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-arm64.h"
index 226ab0d6a5702e53a9252788fcc6f07cce4ef90d..b5979862208a32a61fc594f5b150a183f225df6d 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-ia64.h"
index a768257ff8f0d503ecbd6cea20fde92c9067cdcf..6d809a79ac54cf488c61faf587a0f5a5d3e50196 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-mips.h"
index c88b95f6ec810974cee7fbf0a33d827e073042eb..174cc620a202c7af27d8012b11075f09d78d93ed 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-ppc.h"
index d5c9d254c3c95cd31648f2e6a44fb66fd1d2e483..19a7fba11017251a55864c39a93fa94ff5b5b2de 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-s390x.h"
index d0456db5494386cf893d21d13c71dc2054b17ecb..ba849873632cf0798c66c34ecddf2990056d9873 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-sparc.h"
index 57fff00039e71233065291ea2c746de8e2a1d30b..4a96aa3a088eeb3d6a646c123c603bb305c29296 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "mono/utils/mono-hwcap-x86.h"
index 38c032696bb3052623064683ec599073fe63b2c6..a3d2b6078bfdb0d3e401d6e2854497e5ec7f3b8f 100644 (file)
@@ -16,6 +16,7 @@
  * Copyright 2006 Broadcom
  * Copyright 2007-2008 Andreas Faerber
  * Copyright 2011-2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <stdlib.h>
index 99631f08ef68c58f8b0120d0bd95d44b77360473..194eadc15c97f0a0d3541baf85fcd20f72418bf6 100644 (file)
@@ -4,6 +4,7 @@
  * Authors: Ludovic Henry <ludovic@xamarin.com>
  *
  * Copyright 2015 Xamarin, Inc. (www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_LAZY_INIT_H__
index bed9595f84d344e3209521564fc756efcfdb77c9..f076034da21d7f0dc9ff4aa6c3e1e535f20c8ef5 100644 (file)
@@ -126,7 +126,7 @@ try_again:
                                mono_memory_write_barrier ();
                                mono_hazard_pointer_clear (hp, 1);
                                if (list->free_node_func)
-                                       mono_thread_hazardous_free_or_queue (cur, list->free_node_func, list->locking, context);
+                                       mono_thread_hazardous_queue_free (cur, list->free_node_func);
                        } else
                                goto try_again;
                }
@@ -198,7 +198,7 @@ mono_lls_remove (MonoLinkedListSet *list, MonoThreadHazardPointers *hp, MonoLink
                        mono_memory_write_barrier ();
                        mono_hazard_pointer_clear (hp, 1);
                        if (list->free_node_func)
-                               mono_thread_hazardous_free_or_queue (value, list->free_node_func, list->locking, context);
+                               mono_thread_hazardous_try_free (value, list->free_node_func);
                } else
                        mono_lls_find (list, hp, value->key, context);
                return TRUE;
index 6e0d6296fd6b53a04ba05727240d196daab5fb08..947602f0c34e2177d3a829fd6863850208d24c6f 100644 (file)
@@ -152,7 +152,7 @@ mono_lls_filter_accept_all (gpointer elem)
                                                mono_memory_write_barrier (); \
                                                mono_hazard_pointer_clear (hp__, 1); \
                                                if (list__->free_node_func) { \
-                                                       mono_thread_hazardous_free_or_queue (cur__, list__->free_node_func, list__->locking, HAZARD_FREE_ASYNC_CTX); \
+                                                       mono_thread_hazardous_queue_free (cur__, list__->free_node_func); \
                                                } \
                                        } else { \
                                                restart__ = TRUE; \
index 083f41aee33587b4a4b5928869d0fddb0fae548d..fce4e6c2ba693a5340fd455b89ac868208515f52 100644 (file)
@@ -5,6 +5,7 @@
  *     Rodrigo Kumpera (kumpera@gmail.com)
  *
  * Copyright (c) 2011 Novell, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_MONO_MACHINE_H__
index 9762dc5142666639ea57ad2cbeecbf334a39b680..fbb87cff574175996469db0a1ac3b10586a4fcef 100644 (file)
@@ -157,17 +157,17 @@ Acquire/release semantics macros.
 #define mono_atomic_load_release(_type,target) ({      \
        _type __tmp;    \
        LOAD_RELEASE_FENCE;     \
-       __tmp = *target;        \
+       __tmp = *(target);      \
        __tmp; })
 
 #define mono_atomic_load_acquire(var,_type,target) do {        \
-       _type __tmp = *target;  \
+       _type __tmp = *(target);        \
        LOAD_ACQUIRE_FENCE;     \
        (var) = __tmp; \
 } while (0)
 
 #define mono_atomic_store_acquire(target,value) {      \
-       *target = value;        \
+       *(target) = (value);    \
        STORE_ACQUIRE_FENCE;    \
        }
 
index ed6f015a647f369925ccfafda55d6e46d15edc27..faca70b8ca95e655d759182f8538356a5291a8e5 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2014 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_UTILS_MMAP_INTERNAL_H__
index f3b4d17c77bd9104d49c742c56b84d70a1d63eb7..7fa483ce593747f586e4842fed1a720ffeff2dee 100644 (file)
@@ -5,6 +5,7 @@
  *   Mono Team (mono-list@lists.ximian.com)
  *
  * Copyright 2001-2008 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
index 536640532ef52981ad911a9c00a45682702285a7..1317b0b462d385037b2347d881a954dfc201785d 100644 (file)
@@ -5,6 +5,8 @@
  * Authors: Jeffrey Stedfast <fejj@ximian.com>
  *
  * Copyright 2002 Ximian, Inc. (www.ximian.com)
+ *
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_OS_MUTEX_H__
@@ -208,6 +210,11 @@ WINBASEAPI WINBOOL WINAPI InitOnceBeginInitialize(LPINIT_ONCE lpInitOnce, DWORD
 WINBASEAPI WINBOOL WINAPI InitOnceComplete(LPINIT_ONCE lpInitOnce, DWORD dwFlags, LPVOID lpContext);
 WINBASEAPI WINBOOL WINAPI InitOnceExecuteOnce(PINIT_ONCE InitOnce, PINIT_ONCE_FN InitFn, PVOID Parameter, LPVOID *Context);
 
+/* https://msdn.microsoft.com/en-us/library/windows/desktop/ms683477(v=vs.85).aspx */
+WINBASEAPI BOOL WINAPI InitializeCriticalSectionEx(LPCRITICAL_SECTION lpCriticalSection, DWORD dwSpinCount, DWORD Flags);
+
+#define CRITICAL_SECTION_NO_DEBUG_INFO 0x01000000
+
 #endif /* defined __MINGW32__ && !defined __MINGW64_VERSION_MAJOR && (_WIN32_WINNT >= 0x0600) */
 
 typedef CRITICAL_SECTION mono_mutex_t;
@@ -216,14 +223,14 @@ typedef CONDITION_VARIABLE mono_cond_t;
 static inline int
 mono_os_mutex_init (mono_mutex_t *mutex)
 {
-       InitializeCriticalSection (mutex);
+       InitializeCriticalSectionEx (mutex, 0, CRITICAL_SECTION_NO_DEBUG_INFO);
        return 0;
 }
 
 static inline int
 mono_os_mutex_init_recursive (mono_mutex_t *mutex)
 {
-       InitializeCriticalSection (mutex);
+       InitializeCriticalSectionEx (mutex, 0, CRITICAL_SECTION_NO_DEBUG_INFO);
        return 0;
 }
 
index 7ab1b9df7876d24e2bf88fe0858c177491512bcf..16e3d463b8b7377ab0dfb6ec22b8adcc15b76f66 100644 (file)
@@ -131,10 +131,13 @@ static inline int
 mono_os_sem_post (MonoSemType *sem)
 {
        int res;
-
+retry:
        res = semaphore_signal (*sem);
        g_assert (res != KERN_INVALID_ARGUMENT);
 
+       if (res == KERN_ABORTED)
+               goto retry;
+
        return res != KERN_SUCCESS ? -1 : 0;
 }
 
index 9b8585a392afdda7bca558220f32fb24d81dbcf5..efd732d6d56b7592b9de709a4d34c352e42baf8f 100644 (file)
@@ -1,6 +1,7 @@
 /*
  * Copyright 2008-2011 Novell Inc
  * Copyright 2011 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include "config.h"
@@ -26,6 +27,7 @@
 #if defined(_POSIX_VERSION)
 #include <sys/errno.h>
 #include <sys/param.h>
+#include <errno.h>
 #ifdef HAVE_SYS_TYPES_H
 #include <sys/types.h>
 #endif
@@ -354,22 +356,35 @@ get_process_stat_item (int pid, int pos, int sum, MonoProcessError *error)
        mach_msg_type_number_t t_info_count = TASK_BASIC_INFO_COUNT, th_count;
        thread_array_t th_array;
        size_t i;
+       kern_return_t ret;
 
        if (pid == getpid ()) {
                /* task_for_pid () doesn't work on ios, even for the current process */
                task = mach_task_self ();
        } else {
-               if (task_for_pid (mach_task_self (), pid, &task) != KERN_SUCCESS)
+               do {
+                       ret = task_for_pid (mach_task_self (), pid, &task);
+               } while (ret == KERN_ABORTED);
+
+               if (ret != KERN_SUCCESS)
                        RET_ERROR (MONO_PROCESS_ERROR_NOT_FOUND);
        }
 
-       if (task_info (task, TASK_BASIC_INFO, (task_info_t)&t_info, &t_info_count) != KERN_SUCCESS) {
+       do {
+               ret = task_info (task, TASK_BASIC_INFO, (task_info_t)&t_info, &t_info_count);
+       } while (ret == KERN_ABORTED);
+
+       if (ret != KERN_SUCCESS) {
                if (pid != getpid ())
                        mach_port_deallocate (mach_task_self (), task);
                RET_ERROR (MONO_PROCESS_ERROR_OTHER);
        }
+
+       do {
+               ret = task_threads (task, &th_array, &th_count);
+       } while (ret == KERN_ABORTED);
        
-       if (task_threads(task, &th_array, &th_count) != KERN_SUCCESS) {
+       if (ret  != KERN_SUCCESS) {
                if (pid != getpid ())
                        mach_port_deallocate (mach_task_self (), task);
                RET_ERROR (MONO_PROCESS_ERROR_OTHER);
@@ -380,7 +395,11 @@ get_process_stat_item (int pid, int pos, int sum, MonoProcessError *error)
                
                struct thread_basic_info th_info;
                mach_msg_type_number_t th_info_count = THREAD_BASIC_INFO_COUNT;
-               if (thread_info(th_array[i], THREAD_BASIC_INFO, (thread_info_t)&th_info, &th_info_count) == KERN_SUCCESS) {
+               do {
+                       ret = thread_info(th_array[i], THREAD_BASIC_INFO, (thread_info_t)&th_info, &th_info_count);
+               } while (ret == KERN_ABORTED);
+
+               if (ret == KERN_SUCCESS) {
                        thread_user_time = th_info.user_time.seconds + th_info.user_time.microseconds / 1e6;
                        thread_system_time = th_info.system_time.seconds + th_info.system_time.microseconds / 1e6;
                        //thread_percent = (double)th_info.cpu_usage / TH_USAGE_SCALE;
@@ -493,16 +512,25 @@ get_pid_status_item (int pid, const char *item, MonoProcessError *error, int mul
        task_t task;
        struct task_basic_info t_info;
        mach_msg_type_number_t th_count = TASK_BASIC_INFO_COUNT;
+       kern_return_t mach_ret;
 
        if (pid == getpid ()) {
                /* task_for_pid () doesn't work on ios, even for the current process */
                task = mach_task_self ();
        } else {
-               if (task_for_pid (mach_task_self (), pid, &task) != KERN_SUCCESS)
+               do {
+                       mach_ret = task_for_pid (mach_task_self (), pid, &task);
+               } while (mach_ret == KERN_ABORTED);
+
+               if (mach_ret != KERN_SUCCESS)
                        RET_ERROR (MONO_PROCESS_ERROR_NOT_FOUND);
        }
-       
-       if (task_info (task, TASK_BASIC_INFO, (task_info_t)&t_info, &th_count) != KERN_SUCCESS) {
+
+       do {
+               mach_ret = task_info (task, TASK_BASIC_INFO, (task_info_t)&t_info, &th_count);
+       } while (mach_ret == KERN_ABORTED);
+
+       if (mach_ret != KERN_SUCCESS) {
                if (pid != getpid ())
                        mach_port_deallocate (mach_task_self (), task);
                RET_ERROR (MONO_PROCESS_ERROR_OTHER);
index 1e20760e898ebc9ef10350fe86143811b2e92cfe..1e8297750bfb64858fe3f25ec5b5e30bc2b96ede 100644 (file)
@@ -10,6 +10,7 @@
  * Copyright 2001-2003 Ximian, Inc (http://www.ximian.com)
  * Copyright 2004-2009 Novell, Inc (http://www.novell.com)
  * Copyright 2001 Xamarin, Inc (http://www.novell.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 
@@ -123,7 +124,7 @@ mono_rand_try_get_bytes (gpointer *handle, guchar *buffer, gint buffer_size, Mon
                        /* exception will be thrown in managed code */
                        CryptReleaseContext (provider, 0);
                        *handle = 0;
-                       mono_error_set_generic_error (error, "System", "ExecutionEngineException", "Failed to gen random bytes (%d)", GetLastError ());
+                       mono_error_set_execution_engine (error, "Failed to gen random bytes (%d)", GetLastError ());
                        return FALSE;
                }
        }
@@ -186,7 +187,7 @@ get_entropy_from_egd (const char *path, guchar *buffer, int buffer_size, MonoErr
                if (file >= 0)
                        close (file);
                g_warning ("Entropy problem! Can't create or connect to egd socket %s", path);
-               mono_error_set_generic_error (error, "System", "ExecutionEngineException", "Failed to open egd socket %s: %s", path, strerror (err));
+               mono_error_set_execution_engine (error, "Failed to open egd socket %s: %s", path, strerror (err));
                return;
        }
 
@@ -207,7 +208,7 @@ get_entropy_from_egd (const char *path, guchar *buffer, int buffer_size, MonoErr
                        } else {
                                close (file);
                                g_warning ("Send egd request failed %d", err);
-                               mono_error_set_generic_error (error, "System", "ExecutionEngineException", "Failed to send request to egd socket: %s", strerror (err));
+                               mono_error_set_execution_engine (error, "Failed to send request to egd socket: %s", strerror (err));
                                return;
                        }
                }
@@ -225,7 +226,7 @@ get_entropy_from_egd (const char *path, guchar *buffer, int buffer_size, MonoErr
                        } else {
                                close (file);
                                g_warning ("Receive egd request failed %d", err);
-                               mono_error_set_generic_error (error, "System", "ExecutionEngineException", "Failed to get response from egd socket: %s", strerror(err));
+                               mono_error_set_execution_engine (error, "Failed to get response from egd socket: %s", strerror(err));
                                return;
                        }
                }
@@ -295,7 +296,7 @@ mono_rand_try_get_bytes (gpointer *handle, guchar *buffer, gint buffer_size, Mon
                                        continue;
                                g_warning("Entropy error! Error in read (%s).", strerror (errno));
                                /* exception will be thrown in managed code */
-                               mono_error_set_generic_error (error, "System", "ExecutionEngineException", "Entropy error! Error in read (%s).", strerror (errno));
+                               mono_error_set_execution_engine (error, "Entropy error! Error in read (%s).", strerror (errno));
                                return FALSE;
                        }
                        count += err;
index 15106129b7212e85ba809c4a9a13b16332e0d18e..3c2f79b58c37e99ac92e90325b6f603118182aaa 100644 (file)
@@ -201,6 +201,10 @@ typedef struct ucontext {
        #define UCONTEXT_REG_RSI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RSI])
        #define UCONTEXT_REG_RDI(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RDI])
        #define UCONTEXT_REG_RIP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_RIP])
+       #define UCONTEXT_REG_R8(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R8])
+       #define UCONTEXT_REG_R9(ctx)  (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R9])
+       #define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R10])
+       #define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R11])
        #define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R12])
        #define UCONTEXT_REG_R13(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R13])
        #define UCONTEXT_REG_R14(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs [_REG_R14])
@@ -351,6 +355,27 @@ typedef struct ucontext {
        #define UCONTEXT_REG_R11(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_fp)
        #define UCONTEXT_REG_R12(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_ip)
        #define UCONTEXT_REG_CPSR(ctx) (((arm_ucontext*)(ctx))->sig_ctx.arm_cpsr)
+#elif defined(__NetBSD__)
+       typedef ucontext_t arm_ucontext;
+
+       #define UCONTEXT_REG_PC(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_PC])
+       #define UCONTEXT_REG_SP(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_SP])
+       #define UCONTEXT_REG_LR(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_LR])
+       #define UCONTEXT_REG_R0(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R0])
+       #define UCONTEXT_REG_R1(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R1])
+       #define UCONTEXT_REG_R2(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R2])
+       #define UCONTEXT_REG_R3(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R3])
+       #define UCONTEXT_REG_R4(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R4])
+       #define UCONTEXT_REG_R5(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R5])
+       #define UCONTEXT_REG_R6(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R6])
+       #define UCONTEXT_REG_R7(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R7])
+       #define UCONTEXT_REG_R8(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R8])
+       #define UCONTEXT_REG_R9(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R9])
+       #define UCONTEXT_REG_R10(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R10])
+       #define UCONTEXT_REG_R11(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R11])
+       #define UCONTEXT_REG_R12(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_R12])
+       #define UCONTEXT_REG_CPSR(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_CPSR])
+       #define UCONTEXT_REG_VFPREGS(ctx) (((ucontext_t*)(ctx))->uc_mcontext.__gregs[_REG_VFPREGS])
 #endif
 
 #elif defined(TARGET_ARM64)
index fbe798eeb0e6321667023429bfc88b4cb65bb1ce..68fa0ad5f62312b1e11de46d1b92e073f9eeab03 100644 (file)
@@ -2,6 +2,7 @@
  * mono-signal-handler.h: Handle signal handler differences across platforms
  *
  * Copyright (C) 2013 Xamarin Inc
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_SIGNAL_HANDLER_H__
@@ -9,8 +10,49 @@
 
 #include "config.h"
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/utils/mono-signal-handler.h"
+/*
+ * When a signal is delivered to a thread on a Krait Android device
+ * that's in the middle of skipping over an "IT" block, such as this
+ * one:
+ *
+ * 0x40184ef0 <dlfree+1308>:   ldr     r1, [r3, #0]
+ * 0x40184ef2 <dlfree+1310>:   add.w   r5, r12, r2, lsl #3
+ * 0x40184ef6 <dlfree+1314>:   lsls.w  r2, r0, r2
+ * 0x40184efa <dlfree+1318>:   tst     r2, r1
+ * ### this is the IT instruction
+ * 0x40184efc <dlfree+1320>:   itt     eq
+ * 0x40184efe <dlfree+1322>:   orreq   r2, r1
+ * ### signal arrives here
+ * 0x40184f00 <dlfree+1324>:   streq   r2, [r3, #0]
+ * 0x40184f02 <dlfree+1326>:   beq.n   0x40184f1a <dlfree+1350>
+ * 0x40184f04 <dlfree+1328>:   ldr     r2, [r5, #8]
+ * 0x40184f06 <dlfree+1330>:   ldr     r3, [r3, #16]
+ *
+ * then the first few (at most four, one would assume) instructions of
+ * the signal handler (!) might be skipped.  They happen to be the
+ * push of the frame pointer and return address, so once the signal
+ * handler has done its work, it returns into a SIGSEGV.
+ */
+
+#if defined (TARGET_ARM) && defined (HAVE_ARMV7) && defined (TARGET_ANDROID)
+#define KRAIT_IT_BUG_WORKAROUND        1
+#endif
+
+#ifdef KRAIT_IT_BUG_WORKAROUND
+#define MONO_SIGNAL_HANDLER_FUNC(access, name, arglist)                \
+       static void __krait_ ## name arglist;   \
+       __attribute__ ((naked)) access void                             \
+       name arglist                                                    \
+       {                                                               \
+               asm volatile (                                          \
+                             "mov r0, r0\n\t"                          \
+                             "mov r0, r0\n\t"                          \
+                             "mov r0, r0\n\t"                          \
+                             "mov r0, r0\n\t"                          \
+                                 "b __krait_" # name                   \
+                                 "\n\t");                                              \
+       }       \
+       static __attribute__((used)) void __krait_ ## name arglist
 #endif
 
 /* Don't use this */
index 456cb31bb3e7b3aba28590476cafd407483fe949..123f40ba2ada9142574079d10a086586925900e6 100644 (file)
@@ -1,6 +1,7 @@
 /*
  * Copyright 2008-2010 Novell, Inc.
  * Copyright 2011 Xamarin Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 #ifndef __MONO_MONO_STACK_UNWINDING_H__
 #define __MONO_MONO_STACK_UNWINDING_H__
index a72ee81a56075a5d45a8c36fa2ae5a356b2c9171..fa82387f26ff8e01f26dfc12874eeea0a91d56ab 100644 (file)
@@ -2,8 +2,55 @@
 
 #if defined(PLATFORM_ANDROID)
 
-#ifdef ENABLE_EXTENSION_MODULE
-#include "../../../mono-extensions/mono/utils/mono-threads-android.c"
-#endif
+#include <pthread.h>
+#include <stdio.h>
+#include <inttypes.h>
+#include "glib.h"
+
+static void
+slow_get_thread_bounds (guint8 *current, guint8 **staddr, size_t *stsize)
+{
+       char buff [1024];
+       FILE *f = fopen ("/proc/self/maps", "r");
+       if (!f)
+               g_error ("Could not determine thread bounds, failed to open /proc/self/maps");
+
+       while (fgets (buff, sizeof (buff), f)) {
+               intmax_t low, high;
+               char *ptr = buff;
+               char *end = NULL;
+               //each line starts with the range we want: f7648000-f7709000
+               low = strtoimax (ptr, &end, 16);
+               if (end) {
+                       ptr = end + 1; //skip the dash to make sure we don't get a negative number
+                       end = NULL;
+                       high = strtoimax (ptr, &end, 16);
+               }
+               if (end && low <= (intmax_t)(size_t)current && high > (intmax_t)(size_t)current) {
+                       *staddr = (guint8 *)(size_t)low;
+                       *stsize = (size_t)(high - low);
+                       fclose (f);
+                       return;
+               }
+       }
+       g_error ("Could not determine thread bounds, failed to find current stack pointer in /proc/self/maps");
+}
+
+void
+mono_threads_core_get_stack_bounds (guint8 **staddr, size_t *stsize)
+{
+       pthread_attr_t attr;
+       guint8 *current = (guint8*)&attr;
+
+       *staddr = NULL;
+       *stsize = (size_t)-1;
+
+       pthread_getattr_np (pthread_self (), &attr);
+       pthread_attr_getstack (&attr, (void**)staddr, stsize);
+       pthread_attr_destroy (&attr);
+
+       if (*staddr && ((current <= *staddr) || (current > *staddr + *stsize)))
+               slow_get_thread_bounds (current, staddr, stsize);
+}
 
 #endif
index 3b11148aafe3af5d8c7ff2d93368bb3033da1e10..4283537b0f9fa205fcbcd1f5752bdac1ab22afd5 100644 (file)
@@ -5,6 +5,7 @@
  *     Rodrigo Kumpera (kumpera@gmail.com)
  *
  * Copyright 2015 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -25,6 +26,7 @@
 #include <mono/utils/mono-counters.h>
 #include <mono/utils/mono-threads-coop.h>
 #include <mono/utils/mono-threads-api.h>
+#include <mono/utils/checked-build.h>
 
 #ifdef TARGET_OSX
 #include <mono/utils/mach-support.h>
 
 volatile size_t mono_polling_required;
 
+// FIXME: This would be more efficient if instead of instantiating the stack it just pushed a simple depth counter up and down,
+// perhaps with a per-thread cookie in the high bits.
+#ifdef ENABLE_CHECKED_BUILD_GC
+// Maintains a single per-thread stack of ints, used to ensure nesting is not violated
+MonoNativeTlsKey coop_reset_count_stack_key;
+static int coop_tls_push (int v) {
+       GArray *stack = mono_native_tls_get_value (coop_reset_count_stack_key);
+       if (!stack) {
+               stack = g_array_new (FALSE,FALSE,sizeof(int));
+               mono_native_tls_set_value (coop_reset_count_stack_key, stack);
+       }
+       g_array_append_val (stack, v);
+       return stack->len;
+}
+static int coop_tls_pop (int *v) {
+       GArray *stack = mono_native_tls_get_value (coop_reset_count_stack_key);
+       if (!stack || 0 == stack->len)
+               return -1;
+       stack->len--;
+       *v = g_array_index (stack, int, stack->len);
+       int len = stack->len;
+       if (0 == len) {
+               g_array_free (stack,TRUE);
+               mono_native_tls_set_value (coop_reset_count_stack_key, NULL);
+       }
+       return len;
+}
+#endif
+
 static int coop_reset_blocking_count;
 static int coop_try_blocking_count;
 static int coop_do_blocking_count;
@@ -193,9 +224,18 @@ mono_threads_reset_blocking_start (void* stackdata)
        if (!mono_threads_is_coop_enabled ())
                return NULL;
 
+       info = mono_thread_info_current_unchecked ();
+
+#ifdef ENABLE_CHECKED_BUILD_GC
+       int reset_blocking_count = InterlockedIncrement (&coop_reset_blocking_count);
+       // In this mode, the blocking count is used as the reset cookie. We would prefer
+       // (but do not require) this to be unique across invocations and threads.
+       if (reset_blocking_count == 0) // We *do* require it be nonzero
+               reset_blocking_count = coop_reset_blocking_count = 1;
+#else
        ++coop_reset_blocking_count;
+#endif
 
-       info = mono_thread_info_current_unchecked ();
        /* If the thread is not attached, it doesn't make sense prepare for suspend. */
        if (!info || !mono_thread_info_is_live (info))
                return NULL;
@@ -211,28 +251,50 @@ mono_threads_reset_blocking_start (void* stackdata)
                return NULL;
        case AbortBlockingOk:
                info->thread_saved_state [SELF_SUSPEND_STATE_INDEX].valid = FALSE;
-               return info;
+               break;
        case AbortBlockingOkAndPool:
                mono_threads_state_poll ();
-               return info;
+               break;
        default:
                g_error ("Unknown thread state");
        }
+
+#ifdef ENABLE_CHECKED_BUILD_GC
+       if (mono_check_mode_enabled (MONO_CHECK_MODE_GC)) {
+               int level = coop_tls_push (reset_blocking_count);
+               //g_warning("Entering reset nest; level %d; cookie %d\n", level, reset_blocking_count);
+               return (void *)(intptr_t)reset_blocking_count;
+       }
+#endif
+
+       return info;
 }
 
 void
 mono_threads_reset_blocking_end (void *cookie, void* stackdata)
 {
-       MonoThreadInfo *info;
-
        if (!mono_threads_is_coop_enabled ())
                return;
 
-       info = (MonoThreadInfo *)cookie;
-       if (!info)
+       if (!cookie)
                return;
 
-       g_assert (info == mono_thread_info_current_unchecked ());
+#ifdef ENABLE_CHECKED_BUILD_GC
+       if (mono_check_mode_enabled (MONO_CHECK_MODE_GC)) {
+               int received_cookie = (int)(intptr_t)cookie;
+               int desired_cookie;
+               int level = coop_tls_pop (&desired_cookie);
+               //g_warning("Leaving reset nest; back to level %d; desired cookie %d; received cookie %d\n", level, desired_cookie, received_cookie);
+               if (level < 0)
+                       mono_fatal_with_history ("Expected cookie %d but found no stack at all\n", desired_cookie);
+               if (desired_cookie != received_cookie)
+                       mono_fatal_with_history ("Expected cookie %d but received %d\n", desired_cookie, received_cookie);
+       } else // Notice this matches the line after the endif
+#endif
+       {
+               g_assert (((MonoThreadInfo *)cookie) == mono_thread_info_current_unchecked ());
+       }
+
        mono_threads_prepare_blocking (stackdata);
 }
 
@@ -248,6 +310,10 @@ mono_threads_init_coop (void)
        mono_counters_register ("Coop Do Polling", MONO_COUNTER_GC | MONO_COUNTER_INT, &coop_do_polling_count);
        mono_counters_register ("Coop Save Count", MONO_COUNTER_GC | MONO_COUNTER_INT, &coop_save_count);
        //See the above for what's wrong here.
+
+#ifdef ENABLE_CHECKED_BUILD_GC
+       mono_native_tls_alloc (&coop_reset_count_stack_key, NULL);
+#endif
 }
 
 void
index 056a88f150a1cd72b8b5a1fb9d771ae8495c8845..559d2fa63c94525e4c36384bb02213e3ac3155a4 100644 (file)
@@ -49,11 +49,16 @@ mono_threads_core_abort_syscall (MonoThreadInfo *info)
 {
        kern_return_t ret;
 
-       ret = thread_suspend (info->native_handle);
+       do {
+               ret = thread_suspend (info->native_handle);
+       } while (ret == KERN_ABORTED);
+
        if (ret != KERN_SUCCESS)
                return;
 
-       ret = thread_abort_safely (info->native_handle);
+       do {
+               ret = thread_abort_safely (info->native_handle);
+       } while (ret == KERN_ABORTED);
 
        /*
         * We are doing thread_abort when thread_abort_safely returns KERN_SUCCESS because
@@ -66,7 +71,11 @@ mono_threads_core_abort_syscall (MonoThreadInfo *info)
        if (ret == KERN_SUCCESS)
                ret = thread_abort (info->native_handle);
 
-       g_assert (thread_resume (info->native_handle) == KERN_SUCCESS);
+       do {
+               ret = thread_resume (info->native_handle);
+       } while (ret == KERN_ABORTED);
+
+       g_assert (ret == KERN_SUCCESS);
 }
 
 gboolean
index 6f2ddfa78af52357be210b50a2a43c3a73526b52..6c2b07e468f5686872fb4a9db872be7f30dacdd2 100644 (file)
@@ -60,7 +60,11 @@ mono_threads_core_begin_async_suspend (MonoThreadInfo *info, gboolean interrupt_
 
        g_assert (info);
 
-       ret = thread_suspend (info->native_handle);
+
+       do {
+               ret = thread_suspend (info->native_handle);
+       } while (ret == KERN_ABORTED);
+
        THREADS_SUSPEND_DEBUG ("SUSPEND %p -> %d\n", (void*)info->native_handle, ret);
        if (ret != KERN_SUCCESS)
                return FALSE;
@@ -68,7 +72,10 @@ mono_threads_core_begin_async_suspend (MonoThreadInfo *info, gboolean interrupt_
        /* We're in the middle of a self-suspend, resume and register */
        if (!mono_threads_transition_finish_async_suspend (info)) {
                mono_threads_add_to_pending_operation_set (info);
-               g_assert (thread_resume (info->native_handle) == KERN_SUCCESS);
+               do {
+                       ret = thread_resume (info->native_handle);
+               } while (ret == KERN_ABORTED);
+               g_assert (ret == KERN_SUCCESS);
                THREADS_SUSPEND_DEBUG ("FAILSAFE RESUME/1 %p -> %d\n", (void*)info->native_handle, 0);
                //XXX interrupt_kernel doesn't make sense in this case as the target is not in a syscall
                return TRUE;
@@ -81,7 +88,10 @@ mono_threads_core_begin_async_suspend (MonoThreadInfo *info, gboolean interrupt_
                        thread_abort (info->native_handle);
        } else {
                mono_threads_transition_async_suspend_compensation (info);
-               g_assert (thread_resume (info->native_handle) == KERN_SUCCESS);
+               do {
+                       ret = thread_resume (info->native_handle);
+               } while (ret == KERN_ABORTED);
+               g_assert (ret == KERN_SUCCESS);
                THREADS_SUSPEND_DEBUG ("FAILSAFE RESUME/2 %p -> %d\n", (void*)info->native_handle, 0);
        }
        return res;
@@ -112,7 +122,10 @@ mono_threads_core_begin_async_resume (MonoThreadInfo *info)
                state = (thread_state_t) alloca (mono_mach_arch_get_thread_state_size ());
                mctx = (mcontext_t) alloca (mono_mach_arch_get_mcontext_size ());
 
-               ret = mono_mach_arch_get_thread_state (info->native_handle, state, &num_state);
+               do {
+                       ret = mono_mach_arch_get_thread_state (info->native_handle, state, &num_state);
+               } while (ret == KERN_ABORTED);
+
                if (ret != KERN_SUCCESS)
                        return FALSE;
 
@@ -122,12 +135,17 @@ mono_threads_core_begin_async_resume (MonoThreadInfo *info)
 
                mono_mach_arch_mcontext_to_thread_state (mctx, state);
 
-               ret = mono_mach_arch_set_thread_state (info->native_handle, state, num_state);
+               do {
+                       ret = mono_mach_arch_set_thread_state (info->native_handle, state, num_state);
+               } while (ret == KERN_ABORTED);
+
                if (ret != KERN_SUCCESS)
                        return FALSE;
        }
 
-       ret = thread_resume (info->native_handle);
+       do {
+               ret = thread_resume (info->native_handle);
+       } while (ret == KERN_ABORTED);
        THREADS_SUSPEND_DEBUG ("RESUME %p -> %d\n", (void*)info->native_handle, ret);
 
        return ret == KERN_SUCCESS;
index 39caeb54d65b68c918bdc04f991d2a53c4163e13..8200b101913cc05c9e612c69a2077737a5a5ac85 100644 (file)
@@ -36,8 +36,8 @@ static sigset_t suspend_ack_signal_mask;
 //Can't avoid the circular dep on this. Will be gone pretty soon
 extern int mono_gc_get_suspend_signal (void);
 
-static int
-signal_search_alternative (int min_signal)
+int
+mono_threads_posix_signal_search_alternative (int min_signal)
 {
 #if !defined (SIGRTMIN)
        g_error ("signal search only works with RTMIN");
@@ -88,7 +88,7 @@ suspend_signal_get (void)
 #else
        static int suspend_signum = -1;
        if (suspend_signum == -1)
-               suspend_signum = signal_search_alternative (-1);
+               suspend_signum = mono_threads_posix_signal_search_alternative (-1);
        return suspend_signum;
 #endif /* SIGRTMIN */
 }
@@ -107,7 +107,7 @@ restart_signal_get (void)
 #else
        static int resume_signum = -1;
        if (resume_signum == -1)
-               resume_signum = signal_search_alternative (suspend_signal_get () + 1);
+               resume_signum = mono_threads_posix_signal_search_alternative (suspend_signal_get () + 1);
        return resume_signum;
 #endif /* SIGRTMIN */
 }
@@ -127,7 +127,7 @@ abort_signal_get (void)
 #else
        static int abort_signum = -1;
        if (abort_signum == -1)
-               abort_signum = signal_search_alternative (restart_signal_get () + 1);
+               abort_signum = mono_threads_posix_signal_search_alternative (restart_signal_get () + 1);
        return abort_signum;
 #endif /* SIGRTMIN */
 }
index 2bdcf8e789ac29e055359ce26c8a4dfb5c406bba..59a38c1ceb21fcf922d109ffdff71091415978a5 100644 (file)
@@ -14,6 +14,9 @@ typedef enum {
        MONO_THREADS_POSIX_INIT_SIGNALS_ABORT,
 } MonoThreadPosixInitSignals;
 
+int
+mono_threads_posix_signal_search_alternative (int min_signal);
+
 void
 mono_threads_posix_init_signals (MonoThreadPosixInitSignals signals);
 
@@ -28,4 +31,4 @@ mono_threads_posix_get_abort_signal (void);
 
 #endif /* defined(USE_POSIX_BACKEND) || defined(USE_POSIX_SYSCALL_ABORT) */
 
-#endif /* __MONO_THREADS_POSIX_SIGNALS_H__ */
\ No newline at end of file
+#endif /* __MONO_THREADS_POSIX_SIGNALS_H__ */
index 54f183e58f03659937730f70797d3de5b411c0db..395fdb5bdab19dacdf2de564c7e8fa534cd9b936 100644 (file)
@@ -279,7 +279,34 @@ mono_native_thread_create (MonoNativeThreadId *tid, gpointer func, gpointer arg)
 void
 mono_threads_core_set_name (MonoNativeThreadId tid, const char *name)
 {
-#if defined (HAVE_PTHREAD_SETNAME_NP) && !defined (__MACH__)
+#ifdef __MACH__
+       /*
+        * We can't set the thread name for other threads, but we can at least make
+        * it work for threads that try to change their own name.
+        */
+       if (tid != mono_native_thread_id_get ())
+               return;
+
+       if (!name) {
+               pthread_setname_np ("");
+       } else {
+               char n [63];
+
+               strncpy (n, name, 63);
+               n [62] = '\0';
+               pthread_setname_np (n);
+       }
+#elif defined (__NetBSD__)
+       if (!name) {
+               pthread_setname_np (tid, "%s", (void*)"");
+       } else {
+               char n [PTHREAD_MAX_NAMELEN_NP];
+
+               strncpy (n, name, PTHREAD_MAX_NAMELEN_NP);
+               n [PTHREAD_MAX_NAMELEN_NP - 1] = '\0';
+               pthread_setname_np (tid, "%s", (void*)n);
+       }
+#elif defined (HAVE_PTHREAD_SETNAME_NP)
        if (!name) {
                pthread_setname_np (tid, "");
        } else {
index d130a13613de89b78e4ee113cec9bc4806f74c9f..32491a4ca225229e622799504f8d7cc6012c031c 100644 (file)
@@ -113,7 +113,7 @@ retry_state_change:
                trace_state_change ("ATTACH", info, raw_state, STATE_RUNNING, 0);
                break;
        default:
-               g_error ("Cannot transition current thread from %s with ATTACH", state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition current thread from %s with ATTACH", state_name (cur_state));
        }
 }
 
@@ -148,7 +148,7 @@ STATE_BLOCKING: This is a bug in the coop code that forgot to do a finish blocki
 STATE_BLOCKING_AND_SUSPENDED: This is a bug in coop x suspend that resulted the thread in an undetachable state.
 */
        default:
-               g_error ("Cannot transition current thread %p from %s with DETACH", info, state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition current thread %p from %s with DETACH", info, state_name (cur_state));
        }
 }
 
@@ -190,7 +190,7 @@ STATE_BLOCKING_AND_SUSPENDED: Self suspension cannot be started when the thread
 If this turns to be an issue we can introduce a new suspend request state for when both have been requested.
 */
        default:
-               g_error ("Cannot transition thread %p from %s with SUSPEND_REQUEST", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with SUSPEND_REQUEST", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -252,7 +252,7 @@ The expected behavior is that the target should poll its state very soon so the
 STATE_ASYNC_SUSPEND_REQUESTED: Since there can only be one async suspend in progress and it must finish, it should not be possible to witness this.
 */
        default:
-               g_error ("Cannot transition thread %p from %s with ASYNC_SUSPEND_REQUESTED", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with ASYNC_SUSPEND_REQUESTED", mono_thread_info_get_tid (info), state_name (cur_state));
        }
        return (MonoRequestAsyncSuspendResult) FALSE;
 }
@@ -301,7 +301,7 @@ STATE_BLOCKING:
 STATE_BLOCKING_AND_SUSPENDED: Pool is a local state transition. No VM activities are allowed while in blocking mode.
 */
        default:
-               g_error ("Cannot transition thread %p from %s with STATE_POLL", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with STATE_POLL", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -401,7 +401,7 @@ If this turns to be a problem we should either implement [2] or make this an inv
 
 */
        default:
-               g_error ("Cannot transition thread %p from %s with REQUEST_RESUME", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with REQUEST_RESUME", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -437,7 +437,7 @@ STATE_SELF_SUSPEND_REQUESTED: When self suspend and async suspend happen togethe
 STATE_BLOCKING: Async suspend only begins if a transition to async suspend requested happened. Blocking would have put us into blocking with positive suspend count if it raced with async finish.
 */
        default:
-               g_error ("Cannot transition thread %p from %s with FINISH_ASYNC_SUSPEND", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with FINISH_ASYNC_SUSPEND", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -481,7 +481,7 @@ STATE_BLOCKING_AND_SUSPENDED
 STATE_SELF_SUSPEND_REQUESTED: All those are invalid end states of a sucessfull finish async suspend
 */
        default:
-               g_error ("Cannot transition thread %p from %s with COMPENSATE_FINISH_ASYNC_SUSPEND", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with COMPENSATE_FINISH_ASYNC_SUSPEND", mono_thread_info_get_tid (info), state_name (cur_state));
 
        }
 }
@@ -526,7 +526,7 @@ STATE_BLOCKING:
 STATE_BLOCKING_AND_SUSPENDED: Blocking is not nestabled
 */
        default:
-               g_error ("Cannot transition thread %p from %s with DO_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with DO_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -574,7 +574,7 @@ STATE_SELF_SUSPEND_REQUESTED: A blocking operation must not be done while trying
 STATE_BLOCKING_AND_SUSPENDED: This an exit state of done blocking
 */
        default:
-               g_error ("Cannot transition thread %p from %s with DONE_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with DONE_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
@@ -624,7 +624,7 @@ STATE_SELF_SUSPEND_REQUESTED: A blocking operation must not be done while trying
 STATE_BLOCKING_AND_SUSPENDED: This is an exit state of done blocking, can't happen here.
 */
        default:
-               g_error ("Cannot transition thread %p from %s with DONE_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
+               mono_fatal_with_history ("Cannot transition thread %p from %s with DONE_BLOCKING", mono_thread_info_get_tid (info), state_name (cur_state));
        }
 }
 
index 5d08308885afd113ee3e52b0abd8b2eb6ed3ead9..b6e70329c96dc4c6f5660c3d071c3b37f8cde78a 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
@@ -424,7 +425,10 @@ unregister_thread (void *arg)
        g_byte_array_free (info->stackdata, /*free_segment=*/TRUE);
 
        /*now it's safe to free the thread info.*/
-       mono_thread_hazardous_free_or_queue (info, free_thread_info, HAZARD_FREE_MAY_LOCK, HAZARD_FREE_SAFE_CTX);
+       mono_thread_hazardous_try_free (info, free_thread_info);
+       /* Pump the HP queue */
+       mono_thread_hazardous_try_free_some ();
+
        mono_thread_small_id_free (small_id);
 }
 
@@ -1515,27 +1519,3 @@ mono_thread_info_describe_interrupt_token (MonoThreadInfo *info, GString *text)
        else
                g_string_append_printf (text, "waiting");
 }
-
-/* info must be self or be held in a hazard pointer. */
-gboolean
-mono_threads_add_async_job (MonoThreadInfo *info, MonoAsyncJob job)
-{
-       MonoAsyncJob old_job;
-       do {
-               old_job = (MonoAsyncJob) info->service_requests;
-               if (old_job & job)
-                       return FALSE;
-       } while (InterlockedCompareExchange (&info->service_requests, old_job | job, old_job) != old_job);
-       return TRUE;
-}
-
-MonoAsyncJob
-mono_threads_consume_async_jobs (void)
-{
-       MonoThreadInfo *info = (MonoThreadInfo*)mono_native_tls_get_value (thread_info_key);
-
-       if (!info)
-               return (MonoAsyncJob) 0;
-
-       return (MonoAsyncJob) InterlockedExchange (&info->service_requests, 0);
-}
index 1019dda1884e4c078e4f9de583e74a339c223bfc..97c77de6e7df32e02c97b643813bec873cbd7dc6 100644 (file)
@@ -164,13 +164,6 @@ enum {
        ASYNC_SUSPEND_STATE_INDEX = 1,
 };
 
-/*
- * This enum tells which async thread service corresponds to which bit.
- */
-typedef enum {
-       MONO_SERVICE_REQUEST_SAMPLE = 1,
-} MonoAsyncJob;
-
 typedef struct _MonoThreadInfoInterruptToken MonoThreadInfoInterruptToken;
 
 typedef struct {
@@ -241,12 +234,6 @@ typedef struct {
        /* Set when the thread is started, or in _wapi_thread_duplicate () */
        HANDLE handle;
 
-       /* Asynchronous service request. This flag is meant to be consumed by the multiplexing signal handlers to discover what sort of work they need to do.
-        * Use the mono_threads_add_async_job and mono_threads_consume_async_jobs APIs to modify this flag.
-        * In the future the signaling should be part of the API, but for now, it's only for massaging the bits.
-        */
-       volatile gint32 service_requests;
-
        void *jit_data;
 
        MonoThreadInfoInterruptToken *interrupt_token;
@@ -346,7 +333,7 @@ mono_thread_info_register_small_id (void);
 THREAD_INFO_TYPE *
 mono_thread_info_attach (void *baseptr);
 
-void
+MONO_API void
 mono_thread_info_detach (void);
 
 gboolean
@@ -370,7 +357,7 @@ mono_thread_info_lookup (MonoNativeThreadId id);
 gboolean
 mono_thread_info_resume (MonoNativeThreadId tid);
 
-void
+MONO_API void
 mono_thread_info_set_name (MonoNativeThreadId tid, const char *name);
 
 void
@@ -466,17 +453,6 @@ mono_threads_get_max_stack_size (void);
 HANDLE
 mono_threads_open_thread_handle (HANDLE handle, MonoNativeThreadId tid);
 
-/*
-This is the async job submission/consumption API.
-XXX: This is a PROVISIONAL API only meant to be used by the statistical profiler.
-If you want to use/extend it anywhere else, understand that you'll have to do some API design work to better fit this puppy.
-*/
-gboolean
-mono_threads_add_async_job (THREAD_INFO_TYPE *info, MonoAsyncJob job);
-
-MonoAsyncJob
-mono_threads_consume_async_jobs (void);
-
 MONO_API void
 mono_threads_attach_tools_thread (void);
 
@@ -547,7 +523,7 @@ void mono_threads_core_set_name (MonoNativeThreadId tid, const char *name);
 void mono_threads_coop_begin_global_suspend (void);
 void mono_threads_coop_end_global_suspend (void);
 
-MonoNativeThreadId
+MONO_API MonoNativeThreadId
 mono_native_thread_id_get (void);
 
 gboolean
index c93130bbdd63994d9c5905c7598ac1b1c6b6b331..5a34f440353e0d8ff72b83443b42412b7d5dda0a 100644 (file)
@@ -2,6 +2,7 @@
  * Time utility functions.
  * Author: Paolo Molaro (<lupus@ximian.com>)
  * Copyright (C) 2008 Novell, Inc.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index 0b6cd5a1a1c65ca11233639be85ac86b13c95715..565b3fe593b6a89fd9908f88e8b3d71424f05da8 100644 (file)
@@ -6,6 +6,7 @@
  *
  * Copyright 2011 Novell, Inc (http://www.novell.com)
  * Copyright 2011 Xamarin, Inc (http://www.xamarin.com)
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_TLS_H__
index 8abe83907ceeb5cbdb419f03c0a12bc92c0365e2..e95f4847e6cf61f0b5ae64e6993212eecde4098a 100644 (file)
@@ -2,26 +2,14 @@
 #define __MONO_BITSET_H__
 
 #include <glib.h>
+#include <mono/utils/mono-compiler.h>
+
 #ifdef SGEN_WITHOUT_MONO
-#include "mono/utils/mono-compiler.h"
 #define MONO_API
 #else
 #include <mono/utils/mono-publib.h>
 #endif
 
-/*
- * When embedding, you have to define MONO_ZERO_LEN_ARRAY before including any
- * other Mono header file if you use a different compiler from the one used to
- * build Mono.
- */
-#ifndef MONO_ZERO_LEN_ARRAY
-#ifdef __GNUC__
-#define MONO_ZERO_LEN_ARRAY 0
-#else
-#define MONO_ZERO_LEN_ARRAY 1
-#endif
-#endif
-
 #define MONO_BITSET_BITS_PER_CHUNK (8 * sizeof (gsize))
 
 typedef struct {
index 0c44c3f6bfae1f47dc13f6365e98381f020f38d2..0bf17f6727b869e51d81ef173de334692914631e 100644 (file)
@@ -3,18 +3,7 @@
  *
  * Copyright (C) 2015 Xamarin Inc
  *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #include <config.h>
index a899908baad9dbd057d1f4de0653693e5ecc8f1f..e2b4a83f39ac7ecd8c8717e977d39812e0efeb74 100644 (file)
@@ -1,20 +1,7 @@
 /*
  * parse.h: Parsing for GC options.
  *
- * Copyright (C) 2015 Xamarin Inc
- *
- * This library is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Library General Public
- * License 2.0 as published by the Free Software Foundation;
- *
- * This library 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
- * Library General Public License for more details.
- *
- * You should have received a copy of the GNU Library General Public
- * License 2.0 along with this library; if not, write to the Free
- * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+ * Licensed under the MIT license. See LICENSE file in the project root for full license information.
  */
 
 #ifndef __MONO_UTILS_PARSE_H__
index 1a541ddea20e453728d1a57dadbdfe178684e2ea..68a0ff55687fc5461ebddaa4d7ee5243583dc12e 100644 (file)
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\mono\mini\mini-amd64-gsharedvt.c">\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\mono\mini\mini-runtime.c" />\r
     <ClCompile Include="..\mono\mini\mini-windows.c" />\r
     <ClCompile Include="..\mono\mini\mini-x86.c">\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|x64'">true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\mono\mini\mini-x86-gsharedvt.c">\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|x64'">true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\mono\mini\mini.c" />\r
     <ClInclude Include="..\mono\metadata\remoting.h" />\r
     <ClInclude Include="..\mono\mini\ir-emit.h" />\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
     </ClInclude>\r
+    <ClInclude Include="..\mono\mini\mini-amd64-gsharedvt.h">\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
+    </ClInclude>\r
     <ClInclude Include="..\mono\mini\mini-x86.h">\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|x64'">true</ExcludedFromBuild>\r
     <ClInclude Include="..\mono\mini\seq-points.h" />\r
     <ClInclude Include="..\mono\mini\version.h" />\r
     <ClInclude Include="..\mono\mini\optflags-def.h" />\r
+    <ClInclude Include="..\mono\mini\cfgdump.h" />\r
+    <ClCompile Include="..\mono\mini\cfgdump.c" />\r
     <ClInclude Include="..\mono\mini\jit-icalls.h " />\r
     <ClCompile Include="..\mono\mini\jit-icalls.c " />\r
     <ClCompile Include="..\mono\mini\seq-points.c" />\r
     <ClCompile Include="..\mono\mini\aot-runtime.c" />\r
     <ClCompile Include="..\mono\mini\graph.c" />\r
     <ClCompile Include="..\mono\mini\mini-codegen.c" />\r
+    <ClCompile Include="..\mono\mini\mini-cross-helpers.c" />\r
     <ClCompile Include="..\mono\mini\mini-exceptions.c" />\r
+    <ClCompile Include="..\mono\mini\mini-exceptions-native-unwinder.c" />\r
     <ClCompile Include="..\mono\mini\mini-trampolines.c  " />\r
     <ClCompile Include="..\mono\mini\tramp-amd64.c">\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\mono\mini\tramp-amd64-gsharedvt.c">\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|Win32'">true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\mono\mini\tramp-x86.c">\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|x64'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>\r
       <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|x64'">true</ExcludedFromBuild>\r
     </ClCompile>\r
+    <ClCompile Include="..\mono\mini\tramp-x86-gsharedvt.c">\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug_SGen|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>\r
+      <ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release_SGen|x64'">true</ExcludedFromBuild>\r
+    </ClCompile>\r
     <ClCompile Include="..\mono\mini\branch-opts.c" />\r
     <ClCompile Include="..\mono\mini\mini-generic-sharing.c" />\r
     <ClInclude Include="..\mono\mini\simd-methods.h" />\r
index 258f984d8e339e04ee1d49141e3f085ff31d6131..d8f354b76079eb2f3d601a0f7ff7e3082a13fc04 100644 (file)
@@ -67,6 +67,7 @@
     <ClCompile Include="..\mono\metadata\mempool.c" />\r
     <ClCompile Include="..\mono\metadata\metadata-verify.c" />\r
     <ClCompile Include="..\mono\metadata\metadata.c" />\r
+    <ClCompile Include="..\mono\metadata\metadata-cross-helpers.c" />\r
     <ClCompile Include="..\mono\metadata\method-builder.c" />\r
     <ClCompile Include="..\mono\metadata\monitor.c" />\r
     <ClCompile Include="..\mono\metadata\mono-basic-block.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-pinning-stats.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-pinning.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-pointer-queue.c" />\r
+    <ClCompile Include="..\mono\sgen\sgen-array-list.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-protocol.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-qsort.c" />\r
     <ClCompile Include="..\mono\sgen\sgen-simple-nursery.c" />\r
     <ClCompile Include="..\mono\metadata\sysmath.c" />\r
     <ClCompile Include="..\mono\metadata\threads.c" />\r
     <ClCompile Include="..\mono\metadata\verify.c" />\r
-    <ClCompile Include="..\mono\mini\mini-cross-helpers.c" />\r
   </ItemGroup>\r
   <ItemGroup>\r
     <ClInclude Include="..\mono\metadata\appdomain.h" />\r
   <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />\r
   <ImportGroup Label="ExtensionTargets">\r
   </ImportGroup>\r
-</Project>
\ No newline at end of file
+</Project>\r
index 17580cece36a95c448fc92237e82bee5f6b1cddb..487513f2c369be8282e3c4a4be25b3af208c821e 100644 (file)
@@ -496,7 +496,7 @@ mono_load_remote_field_new
 mono_lock_free_queue_dequeue
 mono_lock_free_queue_enqueue
 mono_lock_free_queue_init
-mono_lock_free_queue_node_free
+mono_lock_free_queue_node_unpoison
 mono_lock_free_queue_node_init
 mono_locks_dump
 mono_lookup_icall_symbol
@@ -659,6 +659,7 @@ mono_pagesize
 mono_param_get_objects
 mono_parse_default_optimizations
 mono_parse_env_options
+mono_parse_options_from
 mono_path_canonicalize
 mono_path_resolve_symlinks
 mono_pe_file_open
index e4ca56dd9c680869385e9777e64d7618cca228e3..d686ca0d90942115580eb285e3023703273a11f9 100644 (file)
@@ -498,7 +498,7 @@ mono_load_remote_field_new
 mono_lock_free_queue_dequeue
 mono_lock_free_queue_enqueue
 mono_lock_free_queue_init
-mono_lock_free_queue_node_free
+mono_lock_free_queue_node_unpoison
 mono_lock_free_queue_node_init
 mono_locks_dump
 mono_lookup_icall_symbol
@@ -661,6 +661,7 @@ mono_pagesize
 mono_param_get_objects
 mono_parse_default_optimizations
 mono_parse_env_options
+mono_parse_options_from
 mono_path_canonicalize
 mono_path_resolve_symlinks
 mono_pe_file_open
index ff7bc4bfdadb8ed3536d91b0887d16f9a6a2e0d4..a036cf1f8dbc283329b0c3c07ec21baf97d9f750 100644 (file)
@@ -50,6 +50,7 @@
 /mono-abi-info
 /mono-api-diff
 /mono-api-info
+/mono-api-html
 /mono-api-info1
 /mono-api-info2
 /mono-cil-strip
index d23bb676601ade72453fbacac11f8fba9996f1a7..be4d6b164a009018668e73beac1c186eb1666e03 100644 (file)
@@ -84,6 +84,7 @@ scripts_4_0 = \
        mod$(SCRIPT_SUFFIX)                     \
        monolinker$(SCRIPT_SUFFIX)              \
        mono-api-info$(SCRIPT_SUFFIX)           \
+       mono-api-html$(SCRIPT_SUFFIX)           \
        mono-shlib-cop$(SCRIPT_SUFFIX)          \
        mozroots$(SCRIPT_SUFFIX)                \
        permview$(SCRIPT_SUFFIX)                \
diff --git a/scripts/babysitter b/scripts/babysitter
deleted file mode 100755 (executable)
index f8b5a6c..0000000
+++ /dev/null
@@ -1,409 +0,0 @@
-#!/usr/bin/env python
-
-# Mimics GNU timeout, but does some fancy tracking based on custom features in mono nunit24.
-
-import argparse
-import subprocess
-import re
-import signal
-import time
-import sys
-import os.path
-import copy
-import tempfile
-import calendar
-import json
-
-### Constants
-
-# Here is how the communication with nunit works. It has to work with two constraints:
-# - We don't invoke nunit directly. We invoke some Makefile which invokes some other Makefile
-#   and at some point down the line someone calls nunit.
-# - nunit has to be able to report back to us even if (especially if) it terminates improperly.
-# To deal with all this, communication babysitter->nunit is done by environment variables,
-# and communication nunit->babysitter is done by leaving behind files in known locations.
-
-# Filenames
-
-CURRENT_TEST_FILE = "babysitter_report_current_test_file.txt"
-RAN_TEST_FILE     = "babysitter_report_ran_test_file.txt"
-FAILED_TEST_FILE  = "babysitter_report_failed_test_file.txt"
-LOGGING_FILE      = "babysitter_report.json_lines"
-
-# Environment keys
-
-# Keys used for Babysitter<->Nunit IPC
-CURRENT_TEST_KEY  = 'MONO_BABYSITTER_NUNIT_CURRENT_TEST_FILE' # Tell nunit where to leave files
-RAN_TEST_KEY      = 'MONO_BABYSITTER_NUNIT_RAN_TEST_FILE'
-FAILED_TEST_KEY   = 'MONO_BABYSITTER_NUNIT_FAILED_TEST_FILE'
-RUN_KEY           = 'MONO_BABYSITTER_NUNIT_RUN_TEST' # Semicolon-separated list of test names
-RUN_MODE_KEY      = 'MONO_BABYSITTER_NUNIT_RUN_MODE' # Equal to either RUN or AFTER
-
-# Keys used for script configuration (see --help text)
-LOG_FILE_KEY      = 'MONO_BABYSITTER_LOG_FILE'       # Path
-RETRY_KEY         = 'MONO_BABYSITTER_RETRY'          # Equal to an integer
-VERBOSE_KEY       = 'MONO_BABYSITTER_VERBOSE'        # "Undocumented"-- used for debugging babysitter
-
-# JSON keys
-
-DATE_JSON       = 'date'          # POSIX timestamp of test suite run
-INVOKE_JSON     = 'invocation'
-COUNT_JSON      = 'iteration'        # How many times was command executed?
-LIMIT_JSON      = 'failure_max'
-SUPPORT_JSON    = 'babysitter_protocol' # Was the test suite running with a babysitter-aware nunit?
-FINAL_CODE_JSON = 'final_code'
-TESTS_JSON      = 'tests'         # Holds dictionary of (test case name)->(dict with TEST_ keys below)
-TEST_FAILURES         = 'normal_failures'
-TEST_CRASH_FAILURES   = 'crash_failures'
-TEST_TIMEOUT_FAILURES = 'timeout_failures'
-
-### Interpret arguments
-
-scriptname = sys.argv[0]
-
-# This is very silly: This program needs to switch from argparse to manual parsing
-# after the second positional argument, but argparse doesn't let you do this.
-# I work around this with a custom subclass which can selectively swallow errors:
-class Hesitate(Exception):
-       pass
-class HesitantParser(argparse.ArgumentParser):
-       def __init__(s, *args, **kwargs):
-               s.hesitating = True  # Errors will be swallowed until this is set false
-               argparse.ArgumentParser.__init__(s, *args, **kwargs)
-       def error(s, *args, **kwargs):
-               if s.hesitating:
-                       raise Hesitate() # Bail out before errors are printed.
-               argparse.ArgumentParser.error(s, *args, **kwargs)
-
-# Define args
-argparser = HesitantParser(description="""\
-Run a test suite with a timeout.\n
-Durations are floating point numbers followed by an optional unit:\n
-'s' for seconds (the default)
-'m' for minutes
-'h' for hours
-'d' for days\n
-supported environment variables:
-  %s: File to write logs to (as line-delimited JSON)
-  %s: If set to a number, failed test cases will be rerun this many times (NUnit test suites only)""" %
-               (LOG_FILE_KEY, RETRY_KEY),
-       formatter_class=argparse.RawTextHelpFormatter)
-argparser.add_argument('-s', '--signal', dest='signal', metavar='signal', default='TERM',
-       help="Send this signal to the command on timeout, instead of TERM.")
-argparser.add_argument('-k', '--kill-after-duration', dest='kill_after', metavar='duration',
-       help="If process continues running after signal, send KILL after this duration.")
-argparser.add_argument('duration',
-       help="Time to run before sending signal.")
-argparser.add_argument('command', nargs="+", help="Command+args to run.")
-
-# Repeatedly parse the given args until we find the shortest prefix for which parsing succeeds.
-argc = len(sys.argv)
-extra_args = []
-for limit in range(1,argc+1):
-       try:
-               if limit == argc: # On the final pass, parse for real
-                       argparser.hesitating = False
-               args = argparser.parse_args(sys.argv[1:limit])
-               # If we're still here, parse_args succeeded.
-               # The final parsed arg is the command; remaining argv items are its args.
-               extra_args = sys.argv[limit:]
-               break
-       except Hesitate: # Before the final pass, if parse_args fails, skip
-               pass
-
-argparser.hesitating = False # Just act like a normal argparser from here
-
-durationre = re.compile(r'(\d+)([smhd]?)')
-def parse_duration(duration): # Accept units
-       match = durationre.match(duration)
-       if not match:
-               argparser.error("Could not understand duration %s" % duration)
-       time, units = match.group(1), match.group(2)
-       time = int(time)
-       if units == 'm':
-               time *= 60
-       elif units == 'h':
-               time *= 60*60
-       elif units == 'd':
-               time *= 60*60*24
-       return time
-
-def parse_signal(sig):        # Accept names
-       if sig.isdigit():
-               return int(sig)
-       for k,v in signal.__dict__.iteritems():
-               if k == ("SIG%s" % sig):
-                       return v
-       argparser.error("Could not understand signal name %s" % sig)
-
-# Final interpretation of arguments
-duration = parse_duration(args.duration)
-kill_after = parse_duration(args.kill_after) if args.kill_after is not None else None
-timeout_signal = parse_signal(args.signal)
-command = args.command + extra_args
-
-# Process environment
-global_env = copy.deepcopy( os.environ )
-
-verbose = VERBOSE_KEY in global_env
-logging = LOG_FILE_KEY in global_env
-logfile = global_env[LOG_FILE_KEY] if logging else None
-crash_resuming = True # TODO: Consider exposing this option, or adding a retry_on_crash option.
-failmax = int(global_env[RETRY_KEY]) if RETRY_KEY in global_env else 0
-babysitting = True # If false, babysitter becomes a timeout clone with no env manipulation or anything.
-if babysitting:
-       babysitter_dir = tempfile.mkdtemp()
-       global_env[CURRENT_TEST_KEY] = os.path.join(babysitter_dir, CURRENT_TEST_FILE)
-       global_env[RAN_TEST_KEY]     = os.path.join(babysitter_dir, RAN_TEST_FILE)
-       global_env[FAILED_TEST_KEY]  = os.path.join(babysitter_dir, FAILED_TEST_FILE)
-
-have_unix_process_groups = 'killpg' in os.__dict__
-have_windows_process_groups = 'CREATE_NEW_PROCESS_GROUP' in subprocess.__dict__
-
-### Timeout implementation
-
-def wait(proc, duration):
-       # TODO: If we detect Python 3.3, Popen objects have a wait(timeout) method we can use
-       start = time.time()
-       while True:
-               code = proc.poll()
-               if code is not None:
-                       return code
-               if time.time()-start > duration:
-                       return None
-               time.sleep(0.05)
-
-# Popen and send_signal can't be called in their basic forms because we want to
-# send signals to all children, not just to the immediately spawned process.
-# Unfortunately the way to do this varies by operating system.
-def popen(*args, **kwargs):
-       if have_unix_process_groups: # Call function on spawn to become process group leader
-               kwargs['preexec_fn'] = os.setsid
-       elif have_windows_process_groups: # Set magic flag for Windows process groups
-               kwargs['creationflags'] = subprocess.CREATE_NEW_PROCESS_GROUP
-       return subprocess.Popen(*args, **kwargs)
-
-def send_signal(proc, sig):
-       if have_unix_process_groups: # UNIX
-               # For compatibility with GNU timeout, pre-send the signal to just the monitored process
-               os.kill(proc.pid, sig)
-               # Send signal to entire group
-               os.killpg(proc.pid, sig)
-               # For compatibility with GNU Timeout, send a SIGCONT after the signal
-               # (so delivery has a chance to occur even for stopped processes)
-               if sig != signal.SIGKILL and sig != signal.SIGCONT:
-                       os.kill(proc.pid, signal.SIGCONT)
-       elif have_windows_process_groups: # Windows with Python 2.7 or better
-               os.kill(proc.pid, sig) # Becuase CREATE_NEW_PROCESS_GROUP, will go to entire group
-       else: # Windows with Python 2.6-- CREATE_NEW_PROCESS_GROUP not supported
-               proc.send_signal(sig) # No way to contact group, just kill process
-
-### Utility functions
-
-def attemptDelete(path):
-       try:
-               os.remove(path)
-       except OSError:
-               pass
-
-def attemptLines(path):
-       try:
-               with open(path) as f:
-                       return map(lambda s: s.strip('\r\n'), f.readlines())
-       except (OSError, IOError):
-               return []
-
-def attemptFirstLine(path):
-       lines = attemptLines(path)
-       if lines:
-               return lines[0]
-       return None
-
-def posixtime(): # Amazingly, time.time() does not guarantee an epoch in the docs. However this does:
-       return calendar.timegm(time.gmtime())
-
-failcount = {}
-def failure_may_retry(test):
-       if test not in failcount:
-               failcount[test] = 0
-       failcount[test] += 1
-       return failcount[test] < failmax
-
-def verbose_print(arg):
-       if (verbose):
-               print(arg)
-
-def failure_annotate(test):
-       return "%s (failure #%d of %d allowed)" % (test, failcount[test], failmax)
-
-def pluralize(lst):
-       return "s" if len(lst) > 1 else ""
-
-### Run command
-
-def run(): # Returns exit code
-       resume_after = []
-       retry_these = []
-       ever_completed = False
-       died_politely = False
-       proc = None
-       code = None
-
-       # Set up logging
-       log = {DATE_JSON: posixtime(), COUNT_JSON:0, LIMIT_JSON:failmax, SUPPORT_JSON:False,
-               INVOKE_JSON: " ".join(command)}
-
-       def log_value(key, set=None, add=None, target=log): # Call to add toplevel value to log
-               if add is not None:
-                       if key not in target:
-                               target[key] = 0
-                       target[key] += add
-               else:
-                       target[key] = set
-
-       def log_test(testname, key, set=None, add=None):   # Call to add test-case-level value to log
-               if TESTS_JSON not in log:
-                       log[TESTS_JSON] = {}
-               if testname not in log[TESTS_JSON]:
-                       log[TESTS_JSON][testname] = {}
-               log_value(key, set=set, add=add, target=log[TESTS_JSON][testname])
-
-       # Ready to run tests
-       try:
-               while True:
-                       env = copy.copy(global_env)
-                       if ever_completed:
-                               retry_next = []
-                       else: # Persist reported failures list until first non-crash run
-                               retry_next = retry_these
-
-                       log_value(COUNT_JSON, add=1)
-
-                       # Prepare environment/filesystem
-                       if babysitting:
-                               for key in [CURRENT_TEST_KEY, RAN_TEST_KEY, FAILED_TEST_KEY]:
-                                       attemptDelete(env[key])
-                               if resume_after:
-                                       env[RUN_KEY] = ";".join(resume_after)
-                                       env[RUN_MODE_KEY] = "EXCLUDE"
-                               elif retry_these:
-                                       env[RUN_KEY] = ";".join(retry_these)
-                                       env[RUN_MODE_KEY] = "RUN"
-
-                       # Run test suite
-                       try:
-                               proc = popen(command, env=env)
-                       except OSError:
-                               died_politely = True
-                               sys.stderr.write("%s: Could not execute command `%s`\n" % (scriptname, command[0]))
-                               sys.exit(127)
-
-                       code = wait(proc, duration)
-                       timed_out = code is None
-                       if timed_out:                  # Initial timeout
-                               send_signal(proc, timeout_signal)
-                               if kill_after is not None: # Kill-after timeout
-                                       code = wait(proc, kill_after)
-                                       if code is None:
-                                               send_signal(proc, signal.SIGKILL)
-                               code = proc.wait()         # Waits forever
-                               sys.stderr.write("%s: Command `%s` timed out\n" % (scriptname, command[0]))
-                       died_politely = True
-
-                       # The test suite has now run, and what happens next varies:
-                       # 1. The suite either completed fully without failures, or timed out: Just quit.
-                       # 2. The suite crashed (halted without completing):
-                       #   Remember any failures for later and rerun, using a blacklist of testcases we have completed.
-                       # 3. The suite completed, but there were failures reported:
-                       #   Rerun, using a whitelist of only reported-failed testcases.
-                       # 4. The suite crashed partway through a run with a whitelist:
-                       #   Rerun, using a whitelist consisting of the previous whitelist minus successful testcases.
-
-                       crashed_at = attemptFirstLine(env[CURRENT_TEST_KEY])
-                       failed_tests = attemptLines(env[FAILED_TEST_KEY])
-                       ran_tests = attemptLines(env[RAN_TEST_KEY])
-                       bailout = False
-
-                       if crashed_at or failed_tests or ran_tests: # Test suite follows the babysitter protocol
-                               log_value(SUPPORT_JSON, True)
-
-                       if not crashed_at and not ever_completed:  # The resume_after whitelist is only
-                               resume_after = []                      # used before the first noncrashing run
-                               ever_completed = True
-
-                       if timed_out:       # Currently no retries after timeout
-                               bailout = True
-                               code = 124      # See GNU timeout manpage
-
-                       if code or crashed_at: # Process failures
-                               # Handle crash failures
-                               if crashed_at and not timed_out:
-                                       log_test(crashed_at, TEST_CRASH_FAILURES, add=1)
-                                       if not crash_resuming:
-                                               bailout = True
-
-                                       if failure_may_retry(crashed_at):
-                                               if ever_completed:           # Rerun with whitelist next time
-                                                       for test in retry_these: # Prepopulate with last whitelist minus run testcases
-                                                               if test == crashed_at or test not in ran_tests: # (plus crashed testcase)
-                                                                       retry_next.append(test)
-                                               else:                            # Rerun with blacklist next time
-                                                       for test in ran_tests:       # Add testcases we just ran to blacklist
-                                                               if test != crashed_at:   # (except for the crashed testcase)
-                                                                       resume_after.append(test)
-                                       else:
-                                               bailout = True
-
-                               # Handle reported failures
-                               for test in failed_tests:
-                                       log_test(test, TEST_FAILURES, add=1)
-                                       if failure_may_retry(test):
-                                               retry_next.append(test)
-                                       else:
-                                               bailout = True
-
-                               # Report human-readable failures for stdout log.
-                               message = "%s:" % (scriptname)
-                               if timed_out:
-                                       message += " Saw timeout in test case %s (never allowed)." % (crashed_at)
-                               elif crashed_at:
-                                       message += " Saw crash in test case %s." % (failure_annotate(crashed_at))
-                               if failed_tests:
-                                       message += " Saw test failure in test case%s %s." % (pluralize(failed_tests), "; ".join(map(failure_annotate, failed_tests)))
-                               if not (timed_out or crashed_at or failed_tests):
-                                       message += " Test suite terminated with code %d, " % (code)
-                                       if log[SUPPORT_JSON]:
-                                               message += "but failure did not occur during a test case. Halting."
-                                       else:
-                                               message += "and suite cannot report test case data. Halting."
-                               elif bailout:
-                                       message += " Will halt testing."
-                               print(message)
-
-                       if bailout or not (resume_after or retry_next): # If not retrying
-                               return code
-
-                       # If we got here, a retry is occurring
-                       retry_these = retry_next
-
-                       # Report human-readable retry notice for stdout log.
-                       message = "%s: Will rerun test suite" % (scriptname)
-                       if log[COUNT_JSON] > 1:
-                               message += " (iteration #%d)" % (log[COUNT_JSON])
-                       if resume_after:
-                               message += ", resuming at crashed testcase %s." % (crashed_at)
-                       else:
-                               message += ", running previously failed testcase%s: %s." % (pluralize(retry_these), "; ".join(retry_these))
-                       print(message)
-       finally:
-               # Emergency: Ensure command does not outlive this script
-               if proc is not None and not died_politely:
-                       send_signal(proc, signal.SIGKILL)
-
-               # Write out logs
-               log_value(FINAL_CODE_JSON, "EXCEPTION" if code is None else code)
-               if logging:
-                       with open(logfile, "a") as f:
-                               f.write(json.dumps(log) + os.linesep)
-
-sys.exit( run() )
diff --git a/scripts/ci/babysitter b/scripts/ci/babysitter
new file mode 100755 (executable)
index 0000000..f8b5a6c
--- /dev/null
@@ -0,0 +1,409 @@
+#!/usr/bin/env python
+
+# Mimics GNU timeout, but does some fancy tracking based on custom features in mono nunit24.
+
+import argparse
+import subprocess
+import re
+import signal
+import time
+import sys
+import os.path
+import copy
+import tempfile
+import calendar
+import json
+
+### Constants
+
+# Here is how the communication with nunit works. It has to work with two constraints:
+# - We don't invoke nunit directly. We invoke some Makefile which invokes some other Makefile
+#   and at some point down the line someone calls nunit.
+# - nunit has to be able to report back to us even if (especially if) it terminates improperly.
+# To deal with all this, communication babysitter->nunit is done by environment variables,
+# and communication nunit->babysitter is done by leaving behind files in known locations.
+
+# Filenames
+
+CURRENT_TEST_FILE = "babysitter_report_current_test_file.txt"
+RAN_TEST_FILE     = "babysitter_report_ran_test_file.txt"
+FAILED_TEST_FILE  = "babysitter_report_failed_test_file.txt"
+LOGGING_FILE      = "babysitter_report.json_lines"
+
+# Environment keys
+
+# Keys used for Babysitter<->Nunit IPC
+CURRENT_TEST_KEY  = 'MONO_BABYSITTER_NUNIT_CURRENT_TEST_FILE' # Tell nunit where to leave files
+RAN_TEST_KEY      = 'MONO_BABYSITTER_NUNIT_RAN_TEST_FILE'
+FAILED_TEST_KEY   = 'MONO_BABYSITTER_NUNIT_FAILED_TEST_FILE'
+RUN_KEY           = 'MONO_BABYSITTER_NUNIT_RUN_TEST' # Semicolon-separated list of test names
+RUN_MODE_KEY      = 'MONO_BABYSITTER_NUNIT_RUN_MODE' # Equal to either RUN or AFTER
+
+# Keys used for script configuration (see --help text)
+LOG_FILE_KEY      = 'MONO_BABYSITTER_LOG_FILE'       # Path
+RETRY_KEY         = 'MONO_BABYSITTER_RETRY'          # Equal to an integer
+VERBOSE_KEY       = 'MONO_BABYSITTER_VERBOSE'        # "Undocumented"-- used for debugging babysitter
+
+# JSON keys
+
+DATE_JSON       = 'date'          # POSIX timestamp of test suite run
+INVOKE_JSON     = 'invocation'
+COUNT_JSON      = 'iteration'        # How many times was command executed?
+LIMIT_JSON      = 'failure_max'
+SUPPORT_JSON    = 'babysitter_protocol' # Was the test suite running with a babysitter-aware nunit?
+FINAL_CODE_JSON = 'final_code'
+TESTS_JSON      = 'tests'         # Holds dictionary of (test case name)->(dict with TEST_ keys below)
+TEST_FAILURES         = 'normal_failures'
+TEST_CRASH_FAILURES   = 'crash_failures'
+TEST_TIMEOUT_FAILURES = 'timeout_failures'
+
+### Interpret arguments
+
+scriptname = sys.argv[0]
+
+# This is very silly: This program needs to switch from argparse to manual parsing
+# after the second positional argument, but argparse doesn't let you do this.
+# I work around this with a custom subclass which can selectively swallow errors:
+class Hesitate(Exception):
+       pass
+class HesitantParser(argparse.ArgumentParser):
+       def __init__(s, *args, **kwargs):
+               s.hesitating = True  # Errors will be swallowed until this is set false
+               argparse.ArgumentParser.__init__(s, *args, **kwargs)
+       def error(s, *args, **kwargs):
+               if s.hesitating:
+                       raise Hesitate() # Bail out before errors are printed.
+               argparse.ArgumentParser.error(s, *args, **kwargs)
+
+# Define args
+argparser = HesitantParser(description="""\
+Run a test suite with a timeout.\n
+Durations are floating point numbers followed by an optional unit:\n
+'s' for seconds (the default)
+'m' for minutes
+'h' for hours
+'d' for days\n
+supported environment variables:
+  %s: File to write logs to (as line-delimited JSON)
+  %s: If set to a number, failed test cases will be rerun this many times (NUnit test suites only)""" %
+               (LOG_FILE_KEY, RETRY_KEY),
+       formatter_class=argparse.RawTextHelpFormatter)
+argparser.add_argument('-s', '--signal', dest='signal', metavar='signal', default='TERM',
+       help="Send this signal to the command on timeout, instead of TERM.")
+argparser.add_argument('-k', '--kill-after-duration', dest='kill_after', metavar='duration',
+       help="If process continues running after signal, send KILL after this duration.")
+argparser.add_argument('duration',
+       help="Time to run before sending signal.")
+argparser.add_argument('command', nargs="+", help="Command+args to run.")
+
+# Repeatedly parse the given args until we find the shortest prefix for which parsing succeeds.
+argc = len(sys.argv)
+extra_args = []
+for limit in range(1,argc+1):
+       try:
+               if limit == argc: # On the final pass, parse for real
+                       argparser.hesitating = False
+               args = argparser.parse_args(sys.argv[1:limit])
+               # If we're still here, parse_args succeeded.
+               # The final parsed arg is the command; remaining argv items are its args.
+               extra_args = sys.argv[limit:]
+               break
+       except Hesitate: # Before the final pass, if parse_args fails, skip
+               pass
+
+argparser.hesitating = False # Just act like a normal argparser from here
+
+durationre = re.compile(r'(\d+)([smhd]?)')
+def parse_duration(duration): # Accept units
+       match = durationre.match(duration)
+       if not match:
+               argparser.error("Could not understand duration %s" % duration)
+       time, units = match.group(1), match.group(2)
+       time = int(time)
+       if units == 'm':
+               time *= 60
+       elif units == 'h':
+               time *= 60*60
+       elif units == 'd':
+               time *= 60*60*24
+       return time
+
+def parse_signal(sig):        # Accept names
+       if sig.isdigit():
+               return int(sig)
+       for k,v in signal.__dict__.iteritems():
+               if k == ("SIG%s" % sig):
+                       return v
+       argparser.error("Could not understand signal name %s" % sig)
+
+# Final interpretation of arguments
+duration = parse_duration(args.duration)
+kill_after = parse_duration(args.kill_after) if args.kill_after is not None else None
+timeout_signal = parse_signal(args.signal)
+command = args.command + extra_args
+
+# Process environment
+global_env = copy.deepcopy( os.environ )
+
+verbose = VERBOSE_KEY in global_env
+logging = LOG_FILE_KEY in global_env
+logfile = global_env[LOG_FILE_KEY] if logging else None
+crash_resuming = True # TODO: Consider exposing this option, or adding a retry_on_crash option.
+failmax = int(global_env[RETRY_KEY]) if RETRY_KEY in global_env else 0
+babysitting = True # If false, babysitter becomes a timeout clone with no env manipulation or anything.
+if babysitting:
+       babysitter_dir = tempfile.mkdtemp()
+       global_env[CURRENT_TEST_KEY] = os.path.join(babysitter_dir, CURRENT_TEST_FILE)
+       global_env[RAN_TEST_KEY]     = os.path.join(babysitter_dir, RAN_TEST_FILE)
+       global_env[FAILED_TEST_KEY]  = os.path.join(babysitter_dir, FAILED_TEST_FILE)
+
+have_unix_process_groups = 'killpg' in os.__dict__
+have_windows_process_groups = 'CREATE_NEW_PROCESS_GROUP' in subprocess.__dict__
+
+### Timeout implementation
+
+def wait(proc, duration):
+       # TODO: If we detect Python 3.3, Popen objects have a wait(timeout) method we can use
+       start = time.time()
+       while True:
+               code = proc.poll()
+               if code is not None:
+                       return code
+               if time.time()-start > duration:
+                       return None
+               time.sleep(0.05)
+
+# Popen and send_signal can't be called in their basic forms because we want to
+# send signals to all children, not just to the immediately spawned process.
+# Unfortunately the way to do this varies by operating system.
+def popen(*args, **kwargs):
+       if have_unix_process_groups: # Call function on spawn to become process group leader
+               kwargs['preexec_fn'] = os.setsid
+       elif have_windows_process_groups: # Set magic flag for Windows process groups
+               kwargs['creationflags'] = subprocess.CREATE_NEW_PROCESS_GROUP
+       return subprocess.Popen(*args, **kwargs)
+
+def send_signal(proc, sig):
+       if have_unix_process_groups: # UNIX
+               # For compatibility with GNU timeout, pre-send the signal to just the monitored process
+               os.kill(proc.pid, sig)
+               # Send signal to entire group
+               os.killpg(proc.pid, sig)
+               # For compatibility with GNU Timeout, send a SIGCONT after the signal
+               # (so delivery has a chance to occur even for stopped processes)
+               if sig != signal.SIGKILL and sig != signal.SIGCONT:
+                       os.kill(proc.pid, signal.SIGCONT)
+       elif have_windows_process_groups: # Windows with Python 2.7 or better
+               os.kill(proc.pid, sig) # Becuase CREATE_NEW_PROCESS_GROUP, will go to entire group
+       else: # Windows with Python 2.6-- CREATE_NEW_PROCESS_GROUP not supported
+               proc.send_signal(sig) # No way to contact group, just kill process
+
+### Utility functions
+
+def attemptDelete(path):
+       try:
+               os.remove(path)
+       except OSError:
+               pass
+
+def attemptLines(path):
+       try:
+               with open(path) as f:
+                       return map(lambda s: s.strip('\r\n'), f.readlines())
+       except (OSError, IOError):
+               return []
+
+def attemptFirstLine(path):
+       lines = attemptLines(path)
+       if lines:
+               return lines[0]
+       return None
+
+def posixtime(): # Amazingly, time.time() does not guarantee an epoch in the docs. However this does:
+       return calendar.timegm(time.gmtime())
+
+failcount = {}
+def failure_may_retry(test):
+       if test not in failcount:
+               failcount[test] = 0
+       failcount[test] += 1
+       return failcount[test] < failmax
+
+def verbose_print(arg):
+       if (verbose):
+               print(arg)
+
+def failure_annotate(test):
+       return "%s (failure #%d of %d allowed)" % (test, failcount[test], failmax)
+
+def pluralize(lst):
+       return "s" if len(lst) > 1 else ""
+
+### Run command
+
+def run(): # Returns exit code
+       resume_after = []
+       retry_these = []
+       ever_completed = False
+       died_politely = False
+       proc = None
+       code = None
+
+       # Set up logging
+       log = {DATE_JSON: posixtime(), COUNT_JSON:0, LIMIT_JSON:failmax, SUPPORT_JSON:False,
+               INVOKE_JSON: " ".join(command)}
+
+       def log_value(key, set=None, add=None, target=log): # Call to add toplevel value to log
+               if add is not None:
+                       if key not in target:
+                               target[key] = 0
+                       target[key] += add
+               else:
+                       target[key] = set
+
+       def log_test(testname, key, set=None, add=None):   # Call to add test-case-level value to log
+               if TESTS_JSON not in log:
+                       log[TESTS_JSON] = {}
+               if testname not in log[TESTS_JSON]:
+                       log[TESTS_JSON][testname] = {}
+               log_value(key, set=set, add=add, target=log[TESTS_JSON][testname])
+
+       # Ready to run tests
+       try:
+               while True:
+                       env = copy.copy(global_env)
+                       if ever_completed:
+                               retry_next = []
+                       else: # Persist reported failures list until first non-crash run
+                               retry_next = retry_these
+
+                       log_value(COUNT_JSON, add=1)
+
+                       # Prepare environment/filesystem
+                       if babysitting:
+                               for key in [CURRENT_TEST_KEY, RAN_TEST_KEY, FAILED_TEST_KEY]:
+                                       attemptDelete(env[key])
+                               if resume_after:
+                                       env[RUN_KEY] = ";".join(resume_after)
+                                       env[RUN_MODE_KEY] = "EXCLUDE"
+                               elif retry_these:
+                                       env[RUN_KEY] = ";".join(retry_these)
+                                       env[RUN_MODE_KEY] = "RUN"
+
+                       # Run test suite
+                       try:
+                               proc = popen(command, env=env)
+                       except OSError:
+                               died_politely = True
+                               sys.stderr.write("%s: Could not execute command `%s`\n" % (scriptname, command[0]))
+                               sys.exit(127)
+
+                       code = wait(proc, duration)
+                       timed_out = code is None
+                       if timed_out:                  # Initial timeout
+                               send_signal(proc, timeout_signal)
+                               if kill_after is not None: # Kill-after timeout
+                                       code = wait(proc, kill_after)
+                                       if code is None:
+                                               send_signal(proc, signal.SIGKILL)
+                               code = proc.wait()         # Waits forever
+                               sys.stderr.write("%s: Command `%s` timed out\n" % (scriptname, command[0]))
+                       died_politely = True
+
+                       # The test suite has now run, and what happens next varies:
+                       # 1. The suite either completed fully without failures, or timed out: Just quit.
+                       # 2. The suite crashed (halted without completing):
+                       #   Remember any failures for later and rerun, using a blacklist of testcases we have completed.
+                       # 3. The suite completed, but there were failures reported:
+                       #   Rerun, using a whitelist of only reported-failed testcases.
+                       # 4. The suite crashed partway through a run with a whitelist:
+                       #   Rerun, using a whitelist consisting of the previous whitelist minus successful testcases.
+
+                       crashed_at = attemptFirstLine(env[CURRENT_TEST_KEY])
+                       failed_tests = attemptLines(env[FAILED_TEST_KEY])
+                       ran_tests = attemptLines(env[RAN_TEST_KEY])
+                       bailout = False
+
+                       if crashed_at or failed_tests or ran_tests: # Test suite follows the babysitter protocol
+                               log_value(SUPPORT_JSON, True)
+
+                       if not crashed_at and not ever_completed:  # The resume_after whitelist is only
+                               resume_after = []                      # used before the first noncrashing run
+                               ever_completed = True
+
+                       if timed_out:       # Currently no retries after timeout
+                               bailout = True
+                               code = 124      # See GNU timeout manpage
+
+                       if code or crashed_at: # Process failures
+                               # Handle crash failures
+                               if crashed_at and not timed_out:
+                                       log_test(crashed_at, TEST_CRASH_FAILURES, add=1)
+                                       if not crash_resuming:
+                                               bailout = True
+
+                                       if failure_may_retry(crashed_at):
+                                               if ever_completed:           # Rerun with whitelist next time
+                                                       for test in retry_these: # Prepopulate with last whitelist minus run testcases
+                                                               if test == crashed_at or test not in ran_tests: # (plus crashed testcase)
+                                                                       retry_next.append(test)
+                                               else:                            # Rerun with blacklist next time
+                                                       for test in ran_tests:       # Add testcases we just ran to blacklist
+                                                               if test != crashed_at:   # (except for the crashed testcase)
+                                                                       resume_after.append(test)
+                                       else:
+                                               bailout = True
+
+                               # Handle reported failures
+                               for test in failed_tests:
+                                       log_test(test, TEST_FAILURES, add=1)
+                                       if failure_may_retry(test):
+                                               retry_next.append(test)
+                                       else:
+                                               bailout = True
+
+                               # Report human-readable failures for stdout log.
+                               message = "%s:" % (scriptname)
+                               if timed_out:
+                                       message += " Saw timeout in test case %s (never allowed)." % (crashed_at)
+                               elif crashed_at:
+                                       message += " Saw crash in test case %s." % (failure_annotate(crashed_at))
+                               if failed_tests:
+                                       message += " Saw test failure in test case%s %s." % (pluralize(failed_tests), "; ".join(map(failure_annotate, failed_tests)))
+                               if not (timed_out or crashed_at or failed_tests):
+                                       message += " Test suite terminated with code %d, " % (code)
+                                       if log[SUPPORT_JSON]:
+                                               message += "but failure did not occur during a test case. Halting."
+                                       else:
+                                               message += "and suite cannot report test case data. Halting."
+                               elif bailout:
+                                       message += " Will halt testing."
+                               print(message)
+
+                       if bailout or not (resume_after or retry_next): # If not retrying
+                               return code
+
+                       # If we got here, a retry is occurring
+                       retry_these = retry_next
+
+                       # Report human-readable retry notice for stdout log.
+                       message = "%s: Will rerun test suite" % (scriptname)
+                       if log[COUNT_JSON] > 1:
+                               message += " (iteration #%d)" % (log[COUNT_JSON])
+                       if resume_after:
+                               message += ", resuming at crashed testcase %s." % (crashed_at)
+                       else:
+                               message += ", running previously failed testcase%s: %s." % (pluralize(retry_these), "; ".join(retry_these))
+                       print(message)
+       finally:
+               # Emergency: Ensure command does not outlive this script
+               if proc is not None and not died_politely:
+                       send_signal(proc, signal.SIGKILL)
+
+               # Write out logs
+               log_value(FINAL_CODE_JSON, "EXCEPTION" if code is None else code)
+               if logging:
+                       with open(logfile, "a") as f:
+                               f.write(json.dumps(log) + os.linesep)
+
+sys.exit( run() )
diff --git a/scripts/ci/run-jenkins.sh b/scripts/ci/run-jenkins.sh
new file mode 100755 (executable)
index 0000000..81945bf
--- /dev/null
@@ -0,0 +1,113 @@
+#!/bin/bash -e
+
+TESTCMD=`dirname "${BASH_SOURCE[0]}"`/run-step.sh
+
+export TEST_HARNESS_VERBOSE=1
+
+if [[ ${label} == 'osx-i386' ]]; then EXTRA_CONF_FLAGS="--with-libgdiplus=/Library/Frameworks/Mono.framework/Versions/Current/lib/libgdiplus.dylib --enable-nls=no --build=i386-apple-darwin11.2.0"; fi
+if [[ ${label} == 'osx-amd64' ]]; then EXTRA_CONF_FLAGS="--with-libgdiplus=/Library/Frameworks/Mono.framework/Versions/Current/lib/libgdiplus.dylib --enable-nls=no"; fi
+if [[ ${label} == 'w32' ]]; then PLATFORM=Win32; EXTRA_CONF_FLAGS="--host=i686-pc-mingw32"; export MONO_EXECUTABLE="`cygpath -u ${WORKSPACE}\\\msvc\\\Win32\\\bin\\\Release_SGen\\\mono-sgen.exe`";fi
+if [[ ${label} == 'w64' ]]; then PLATFORM=x64; EXTRA_CONF_FLAGS="--host=i686-pc-mingw32"; export MONO_EXECUTABLE="`cygpath -u ${WORKSPACE}\\\msvc\\\x64\\\bin\\\Release_SGen\\\mono-sgen.exe`"; fi
+
+if [[ ${label} != w* ]] && [[ ${label} != 'debian-ppc64el' ]] && [[ ${label} != 'centos-s390x' ]];
+    then
+    EXTRA_CONF_FLAGS="$EXTRA_CONF_FLAGS --with-monodroid --with-monotouch --with-monotouch_watch --with-monotouch_tv --with-xammac --with-mobile_static"
+    # only enable the mobile profiles and mobile_static on the main architectures
+fi
+
+if [ -x "/usr/bin/dpkg-architecture" ];
+       then
+       EXTRA_CONF_FLAGS="$EXTRA_CONF_FLAGS --host=`/usr/bin/dpkg-architecture -qDEB_HOST_GNU_TYPE`"
+       #force build arch = dpkg arch, sometimes misdetected
+fi
+
+${TESTCMD} --label=configure --timeout=60m --fatal ./autogen.sh $EXTRA_CONF_FLAGS
+if [[ ${label} == w* ]];
+    then
+    ${TESTCMD} --label=make-msvc --timeout=60m --fatal /cygdrive/c/Program\ Files\ \(x86\)/MSBuild/12.0/Bin/MSBuild.exe /p:Platform=${PLATFORM} /p:Configuration=Release msvc/mono.sln
+    ${TESTCMD} --label=make-msvc-sgen --timeout=60m --fatal /cygdrive/c/Program\ Files\ \(x86\)/MSBuild/12.0/Bin/MSBuild.exe /p:Platform=${PLATFORM} /p:Configuration=Release_SGen msvc/mono.sln
+fi
+${TESTCMD} --label=make --timeout=300m --fatal make -w V=1
+if [[ -n "${ghprbPullId}" ]] && [[ ${label} == w* ]];
+    then
+    exit 0
+    # we don't run the test suite on Windows PRs, we just ensure the build succeeds, so end here
+fi
+${TESTCMD} --label=mini --timeout=5m make -w -C mono/mini -k check
+${TESTCMD} --label=runtime --timeout=120m make -w -C mono/tests -k test-wrench V=1 CI=1
+${TESTCMD} --label=corlib --timeout=30m make -w -C mcs/class/corlib run-test
+${TESTCMD} --label=verify --timeout=15m make -w -C runtime mcs-compileall
+${TESTCMD} --label=profiler --timeout=30m make -w -C mono/profiler -k check
+${TESTCMD} --label=compiler --timeout=30m make -w -C mcs/tests run-test
+${TESTCMD} --label=compiler-errors --timeout=30m make -w -C mcs/errors run-test
+${TESTCMD} --label=System --timeout=10m make -w -C mcs/class/System run-test
+${TESTCMD} --label=System.XML --timeout=5m make -w -C mcs/class/System.XML run-test
+${TESTCMD} --label=Mono.Security --timeout=5m make -w -C mcs/class/Mono.Security run-test
+${TESTCMD} --label=System.Security --timeout=5m make -w -C mcs/class/System.Security run-test
+${TESTCMD} --label=System.Drawing --timeout=5m make -w -C mcs/class/System.Drawing run-test
+if [[ ${label} == osx-* ]]
+then ${TESTCMD} --label=Windows.Forms --skip
+else ${TESTCMD} --label=Windows.Forms --timeout=5m make -w -C mcs/class/System.Windows.Forms run-test
+fi
+${TESTCMD} --label=System.Data --timeout=5m make -w -C mcs/class/System.Data run-test
+${TESTCMD} --label=System.Data.OracleClient --timeout=5m make -w -C mcs/class/System.Data.OracleClient run-test
+${TESTCMD} --label=System.Design --timeout=5m make -w -C mcs/class/System.Design run-test
+${TESTCMD} --label=Mono.Posix --timeout=5m make -w -C mcs/class/Mono.Posix run-test
+${TESTCMD} --label=System.Web --timeout=30m make -w -C mcs/class/System.Web run-test
+${TESTCMD} --label=System.Web.Services --timeout=5m make -w -C mcs/class/System.Web.Services run-test
+${TESTCMD} --label=System.Runtime.SFS --timeout=5m make -w -C mcs/class/System.Runtime.Serialization.Formatters.Soap run-test
+${TESTCMD} --label=System.Runtime.Remoting --timeout=5m make -w -C mcs/class/System.Runtime.Remoting run-test
+${TESTCMD} --label=Cscompmgd --timeout=5m make -w -C mcs/class/Cscompmgd run-test
+${TESTCMD} --label=Commons.Xml.Relaxng --timeout=5m make -w -C mcs/class/Commons.Xml.Relaxng run-test
+${TESTCMD} --label=System.ServiceProcess --timeout=5m make -w -C mcs/class/System.ServiceProcess run-test
+${TESTCMD} --label=I18N.CJK --timeout=5m make -w -C mcs/class/I18N/CJK run-test
+${TESTCMD} --label=I18N.West --timeout=5m make -w -C mcs/class/I18N/West run-test
+${TESTCMD} --label=I18N.MidEast --timeout=5m make -w -C mcs/class/I18N/MidEast run-test
+${TESTCMD} --label=System.DirectoryServices --timeout=5m make -w -C mcs/class/System.DirectoryServices run-test
+${TESTCMD} --label=Microsoft.Build.Engine --timeout=5m make -w -C mcs/class/Microsoft.Build.Engine run-test
+${TESTCMD} --label=Microsoft.Build.Framework --timeout=5m make -w -C mcs/class/Microsoft.Build.Framework run-test
+${TESTCMD} --label=Microsoft.Build.Tasks --timeout=5m make -w -C mcs/class/Microsoft.Build.Tasks run-test
+${TESTCMD} --label=Microsoft.Build.Utilities --timeout=5m make -w -C mcs/class/Microsoft.Build.Utilities run-test
+${TESTCMD} --label=Mono.C5 --timeout=5m make -w -C mcs/class/Mono.C5 run-test
+${TESTCMD} --label=System.Configuration --timeout=5m make -w -C mcs/class/System.Configuration run-test
+${TESTCMD} --label=System.Transactions --timeout=5m make -w -C mcs/class/System.Transactions run-test
+${TESTCMD} --label=System.Web.Extensions --timeout=5m make -w -C mcs/class/System.Web.Extensions run-test
+${TESTCMD} --label=System.Core --timeout=15m make -w -C mcs/class/System.Core run-test
+${TESTCMD} --label=symbolicate --timeout=60m make -w -C mcs/tools/mono-symbolicate check
+${TESTCMD} --label=System.Xml.Linq --timeout=5m make -w -C mcs/class/System.Xml.Linq run-test
+${TESTCMD} --label=System.Data.DSE --timeout=5m make -w -C mcs/class/System.Data.DataSetExtensions run-test
+${TESTCMD} --label=System.Web.Abstractions --timeout=5m make -w -C mcs/class/System.Web.Abstractions run-test
+${TESTCMD} --label=System.Web.Routing --timeout=5m make -w -C mcs/class/System.Web.Routing run-test
+${TESTCMD} --label=System.Runtime.Serialization --timeout=5m make -w -C mcs/class/System.Runtime.Serialization run-test
+${TESTCMD} --label=System.IdentityModel --timeout=5m make -w -C mcs/class/System.IdentityModel run-test
+${TESTCMD} --label=System.ServiceModel --timeout=15m make -w -C mcs/class/System.ServiceModel run-test
+${TESTCMD} --label=System.ServiceModel.Web --timeout=5m make -w -C mcs/class/System.ServiceModel.Web run-test
+${TESTCMD} --label=System.Web.Extensions-standalone --timeout=5m make -w -C mcs/class/System.Web.Extensions run-standalone-test
+${TESTCMD} --label=System.ComponentModel.DataAnnotations --timeout=5m make -w -C mcs/class/System.ComponentModel.DataAnnotations run-test
+${TESTCMD} --label=Mono.CodeContracts --timeout=5m make -w -C mcs/class/Mono.CodeContracts run-test
+${TESTCMD} --label=System.Runtime.Caching --timeout=5m make -w -C mcs/class/System.Runtime.Caching run-test
+${TESTCMD} --label=System.Data.Services --timeout=5m make -w -C mcs/class/System.Data.Services run-test
+${TESTCMD} --label=System.Web.DynamicData --timeout=5m make -w -C mcs/class/System.Web.DynamicData run-test
+${TESTCMD} --label=Mono.CSharp --timeout=5m make -w -C mcs/class/Mono.CSharp run-test
+${TESTCMD} --label=WindowsBase --timeout=5m make -w -C mcs/class/WindowsBase run-test
+${TESTCMD} --label=System.Numerics --timeout=5m make -w -C mcs/class/System.Numerics run-test
+${TESTCMD} --label=System.Runtime.DurableInstancing --timeout=5m make -w -C mcs/class/System.Runtime.DurableInstancing run-test
+${TESTCMD} --label=System.ServiceModel.Discovery --timeout=5m make -w -C mcs/class/System.ServiceModel.Discovery run-test
+${TESTCMD} --label=System.Xaml --timeout=5m make -w -C mcs/class/System.Xaml run-test
+${TESTCMD} --label=System.Net.Http --timeout=5m make -w -C mcs/class/System.Net.Http run-test
+${TESTCMD} --label=System.Json --timeout=5m make -w -C mcs/class/System.Json run-test
+${TESTCMD} --label=System.Threading.Tasks.Dataflow --timeout=5m make -w -C mcs/class/System.Threading.Tasks.Dataflow run-test
+${TESTCMD} --label=Mono.Debugger.Soft --timeout=5m make -w -C mcs/class/Mono.Debugger.Soft run-test
+${TESTCMD} --label=Microsoft.Build --timeout=5m make -w -C mcs/class/Microsoft.Build run-test
+${TESTCMD} --label=monodoc --timeout=10m make -w -C mcs/tools/mdoc run-test
+${TESTCMD} --label=Microsoft.Build-12 --timeout=10m make -w -C mcs/class/Microsoft.Build run-test PROFILE=xbuild_12
+${TESTCMD} --label=Microsoft.Build.Engine-12 --timeout=60m make -w -C mcs/class/Microsoft.Build.Engine run-test PROFILE=xbuild_12
+${TESTCMD} --label=Microsoft.Build.Framework-12 --timeout=60m make -w -C mcs/class/Microsoft.Build.Framework run-test PROFILE=xbuild_12
+${TESTCMD} --label=Microsoft.Build.Tasks-12 --timeout=60m make -w -C mcs/class/Microsoft.Build.Tasks run-test PROFILE=xbuild_12
+${TESTCMD} --label=Microsoft.Build.Utilities-12 --timeout=60m make -w -C mcs/class/Microsoft.Build.Utilities run-test PROFILE=xbuild_12
+${TESTCMD} --label=Microsoft.Build-14 --timeout=60m make -w -C mcs/class/Microsoft.Build run-test PROFILE=xbuild_14
+${TESTCMD} --label=Microsoft.Build.Engine-14 --timeout=60m make -w -C mcs/class/Microsoft.Build.Engine run-test PROFILE=xbuild_14
+${TESTCMD} --label=Microsoft.Build.Framework-14 --timeout=60m make -w -C mcs/class/Microsoft.Build.Framework run-test PROFILE=xbuild_14
+${TESTCMD} --label=Microsoft.Build.Tasks-14 --timeout=60m make -w -C mcs/class/Microsoft.Build.Tasks run-test PROFILE=xbuild_14
+${TESTCMD} --label=Microsoft.Build.Utilities-14 --timeout=60m make -w -C mcs/class/Microsoft.Build.Utilities run-test PROFILE=xbuild_14
+rm -fr /tmp/jenkins-temp-aspnet*
diff --git a/scripts/ci/run-step.sh b/scripts/ci/run-step.sh
new file mode 100755 (executable)
index 0000000..115ee12
--- /dev/null
@@ -0,0 +1,60 @@
+#!/bin/bash -e
+TIMEOUTCMD=`dirname "${BASH_SOURCE[0]}"`/babysitter
+if [[ "$OSTYPE" == "cygwin" ]] || ! ${TIMEOUTCMD} -h >/dev/null 2>&1; then
+    TIMEOUTCMD=timeout  # fall back to timeout if babysitter doesn't work (e.g. python not installed or wrong version)
+fi
+
+export MONO_BABYSITTER_LOG_FILE=babysitter_report.json_lines
+
+helptext ()
+{
+    echo "run-step.sh {--label=LABEL} {--skip|--timeout=TIMEOUT [--fatal]} command to run with arguments"
+}
+
+for i in "$@"
+do
+case $i in
+    --help)
+    helptext
+    exit 0
+    ;;
+    --label=*)
+    LABEL="${i#*=}"
+    shift # past argument=value
+    ;;
+    --timeout=*)
+    TIMEOUT="${i#*=}"
+    shift # past argument=value
+    ;;
+    --fatal)
+    FATAL="true"
+    shift # past argument
+    ;;
+    --skip)
+    SKIP="true"
+    shift # past argument
+    ;;
+    *)
+            # unknown option, assume just part of cmdline
+    ;;
+esac
+done
+if [ -n "${SKIP}" ] && [ -z "${LABEL}" ]
+    then helptext
+    exit 1
+fi
+if [ -n "${SKIP}" ]
+    then echo -e "*** start: ${LABEL}\n*** end(0): ${LABEL}: \e[45mSkipped\e[0m"
+    exit 0
+fi
+if [ -z "${LABEL}" ] || [ -z "${TIMEOUT}" ]
+    then helptext
+    exit 1
+fi
+STARTTIME=`date +%s`
+echo "*** start: ${LABEL}"
+if [ -n "${FATAL}" ]; then
+    ${TIMEOUTCMD} --signal=ABRT --kill-after=60s ${TIMEOUT} "$@" && echo -e "*** end($(echo $(date +%s) - ${STARTTIME} | bc)): ${LABEL}: \e[42mPassed\e[0m" || (echo -e "*** end($(echo $(date +%s) - ${STARTTIME} | bc)): ${LABEL}: \e[41mFailed\e[0m" && exit 1)
+else
+    ${TIMEOUTCMD} --signal=ABRT --kill-after=60s ${TIMEOUT} "$@" && echo -e "*** end($(echo $(date +%s) - ${STARTTIME} | bc)): ${LABEL}: \e[42mPassed\e[0m" || echo -e "*** end($(echo $(date +%s) - ${STARTTIME} | bc)): ${LABEL}: \e[43mUnstable\e[0m"
+fi
diff --git a/tools/offsets-tool/.gitignore b/tools/offsets-tool/.gitignore
new file mode 100644 (file)
index 0000000..61a0f8d
--- /dev/null
@@ -0,0 +1,5 @@
+.stamp-clone
+CppSharp
+*.exe
+*.h
+*.exe.mdb
diff --git a/tools/offsets-tool/Makefile b/tools/offsets-tool/Makefile
new file mode 100644 (file)
index 0000000..6486362
--- /dev/null
@@ -0,0 +1,39 @@
+CPPSHARP_DIR = CppSharp
+
+CPPSHARP_REFS = -r:$(CPPSHARP_DIR)/CppSharp.dll \
+       -r:$(CPPSHARP_DIR)/CppSharp.AST.dll \
+       -r:$(CPPSHARP_DIR)/CppSharp.Parser.CSharp.dll \
+       -r:$(CPPSHARP_DIR)/CppSharp.Generator.dll
+
+SRC_ROOT = ../..
+
+MONO_OPTIONS_SRC = $(SRC_ROOT)/mcs/class/Mono.Options/Mono.Options/Options.cs
+
+.stamp-clone:
+       @if [ ! -d $(CPPSHARP_DIR) ]; then \
+               git clone git@github.com:xamarin/CppSharpBinaries.git $(CPPSHARP_DIR); \
+               touch $@; \
+       fi
+
+MonoAotOffsetsDumper.exe: .stamp-clone MonoAotOffsetsDumper.cs $(MONO_OPTIONS_SRC)
+       mcs MonoAotOffsetsDumper.cs /debug /nowarn:0436 $(MONO_OPTIONS_SRC) $(CPPSHARP_REFS)
+
+.PHONY: clean
+clean:
+       rm MonoAotOffsetsDumper.exe
+
+dump: MonoAotOffsetsDumper.exe 
+       MONO_PATH=$(CPPSHARP_DIR) mono MonoAotOffsetsDumper.exe
+
+update:
+       @if [ -f object-offsets.h ]; then rm object-offsets.h; fi;
+       @for f in *.h; do \
+               echo "Processing $$f.."; \
+               echo "#include \"$$f\"" >> object-offsets1.h; \
+       done
+       @cp *.h ../mono/metadata
+
+gen-proj:
+       $(CPPSHARP_DIR)/premake5 vs2012
+
+all: MonoAotOffsetsDumper.exe
\ No newline at end of file
diff --git a/tools/offsets-tool/MonoAotOffsetsDumper.cs b/tools/offsets-tool/MonoAotOffsetsDumper.cs
new file mode 100644 (file)
index 0000000..a5320ba
--- /dev/null
@@ -0,0 +1,822 @@
+using System;
+using System.Collections.Generic;
+using System.IO;
+using System.Linq;
+using System.Text.RegularExpressions;
+using CppSharp.AST;
+using CppSharp.AST.Extensions;
+using CppSharp.Parser;
+
+namespace CppSharp
+{
+    /**
+     * This tool dumps the offsets of structures used in the Mono VM needed
+     * by the AOT compiler for cross-compiling code to target platforms
+     * different than the host the compiler is being invoked on.
+     * 
+     * It takes two arguments: the path to your clone of the Mono repo and
+     * the path to the root of Android NDK.
+     */
+    static class MonoAotOffsetsDumper
+    {
+        static string MonoDir = @"";
+
+        static List<string> Abis = new List<string> ();
+        static string OutputDir;
+
+        static string MonodroidDir = @"";
+        static string MaccoreDir = @"";
+
+        public enum TargetPlatform
+        {
+            Android,
+            iOS,
+            WatchOS,
+        }
+
+        public class Target
+        {
+            public Target()
+            {
+                Defines = new List<string>();
+                Arguments = new List<string>();
+            }
+
+            public Target(Target target)
+            {
+                Platform = target.Platform;
+                Triple = target.Triple;
+                Build = target.Build;
+                Defines = target.Defines;
+                Arguments = target.Arguments;
+            }
+
+            public TargetPlatform Platform;
+            public string Triple;
+            public string Build;            
+            public List<string> Defines;
+            public List<string> Arguments;
+        };
+
+        public static List<Target> Targets = new List<Target>();
+
+        public static IEnumerable<Target> AndroidTargets
+        {
+            get { return Targets.Where ((t) => t.Platform == TargetPlatform.Android); }
+        }
+
+        public static IEnumerable<Target> DarwinTargets
+        {
+            get
+            {
+                return Targets.Where ((t) => t.Platform == TargetPlatform.iOS ||
+                    t.Platform == TargetPlatform.WatchOS);
+            }
+        }
+
+        public static IEnumerable<Target> iOSTargets
+        {
+            get
+            {
+                return Targets.Where ((t) => t.Platform == TargetPlatform.iOS);
+            }
+        }
+
+        public static void SetupAndroidTargets()
+        {
+            Targets.Add (new Target {
+                Platform = TargetPlatform.Android,
+                Triple = "i686-none-linux-android",
+                Build = "mono-x86",
+                Defines = { "TARGET_X86" }
+            });
+
+            Targets.Add (new Target {
+                Platform = TargetPlatform.Android,
+                Triple = "x86_64-none-linux-android",
+                Build = "mono-x86_64",
+                Defines = { "TARGET_AMD64" }
+            });            
+
+            Targets.Add (new Target {
+                Platform = TargetPlatform.Android,
+                Triple = "armv5-none-linux-androideabi",
+                Build = "mono-armv6",
+                Defines = { "TARGET_ARM", "ARM_FPU_VFP", "HAVE_ARMV5" }
+            });
+
+            Targets.Add (new Target {
+                Platform = TargetPlatform.Android,
+                Triple = "armv7-none-linux-androideabi",
+                Build = "mono-armv7",                    
+                Defines = { "TARGET_ARM", "ARM_FPU_VFP", "HAVE_ARMV5", "HAVE_ARMV6",
+                    "HAVE_ARMV7"
+                }
+            });
+
+            Targets.Add (new Target {
+                Platform = TargetPlatform.Android,
+                Triple = "aarch64-v8a-linux-android",
+                Build = "mono-aarch64",                    
+                Defines = { "TARGET_ARM64" }
+            });            
+
+            /*Targets.Add(new Target {
+                    Platform = TargetPlatform.Android,
+                    Triple = "mipsel-none-linux-android",
+                    Build = "mono-mips",
+                    Defines = { "TARGET_MIPS", "__mips__" }
+                });*/
+
+            foreach (var target in AndroidTargets)
+                target.Defines.AddRange (new string[] { "PLATFORM_ANDROID",
+                    "TARGET_ANDROID", "MONO_CROSS_COMPILE", "USE_MONO_CTX"
+                });
+        }
+
+        public static void SetupiOSTargets()
+        {
+            Targets.Add(new Target {
+                Platform = TargetPlatform.iOS,
+                Triple = "arm-apple-darwin10",
+                Build = "target7",
+                Defines = { "TARGET_ARM", "ARM_FPU_VFP", "HAVE_ARMV5" }
+            });
+
+            Targets.Add(new Target {
+                Platform = TargetPlatform.iOS,
+                Triple = "aarch64-apple-darwin10",
+                Build = "target64",                    
+                Defines = { "TARGET_ARM64" }
+            });
+
+            foreach (var target in iOSTargets) {
+                target.Defines.AddRange (new string[] { "PLATFORM_DARWIN",
+                    "TARGET_IOS", "TARGET_MACH", "MONO_CROSS_COMPILE", "USE_MONO_CTX",
+                    "_XOPEN_SOURCE"
+                });
+            }
+
+            Targets.Add(new Target {
+                Platform = TargetPlatform.WatchOS,
+                Triple = "armv7k-apple-darwin",
+                Build = "targetwatch",
+                Defines = { "TARGET_ARM", "ARM_FPU_VFP", "HAVE_ARMV5" }
+            });
+
+            foreach (var target in DarwinTargets) {
+                target.Defines.AddRange (new string[] { "PLATFORM_DARWIN",
+                    "TARGET_IOS", "TARGET_MACH", "MONO_CROSS_COMPILE", "USE_MONO_CTX",
+                    "_XOPEN_SOURCE"
+                });
+            }
+        }
+
+        static bool GetParentSubDirectoryPath(string parent, out string subdir)
+        {
+            var directory = Directory.GetParent(Directory.GetCurrentDirectory());
+
+            while (directory != null) {
+                var path = Path.Combine(directory.FullName, parent);
+
+                if (Directory.Exists (path)) {
+                    subdir = path;
+                    return true;
+                }
+
+                directory = directory.Parent;
+            }
+
+            subdir = null;
+            return false;
+        }
+
+        public static void Main(string[] args)
+        {
+            ParseCommandLineArgs(args);
+
+            string monodroidDir;
+            if (!Directory.Exists (MonodroidDir) &&
+                GetParentSubDirectoryPath ("monodroid", out monodroidDir)) {
+                MonodroidDir = Path.Combine (monodroidDir);
+            }
+
+            if (Directory.Exists (MonodroidDir))
+                SetupAndroidTargets();
+
+            string maccoreDir;
+            if (!Directory.Exists (MaccoreDir) &&
+                GetParentSubDirectoryPath ("maccore", out maccoreDir)) {
+                MaccoreDir = Path.Combine (maccoreDir);
+            }
+
+            if (Directory.Exists(MaccoreDir))
+                SetupiOSTargets();
+
+            foreach (var target in Targets)
+             {
+                if (Abis.Any() && !Abis.Any (target.Triple.Contains))
+                    continue;
+                
+                Console.WriteLine();
+                Console.WriteLine("Processing triple: {0}", target.Triple);
+
+                var options = new DriverOptions();
+
+                var log = new TextDiagnosticPrinter();
+                var driver = new Driver(options, log);
+
+                Setup(driver, target);
+                driver.Setup();
+
+                BuildParseOptions(driver, target);
+                if (!driver.ParseCode())
+                    return;
+
+                Dump(driver.ASTContext, driver.TargetInfo, target);
+            }
+        }
+
+        static void BuildParseOptions(Driver driver, Target target)
+        {
+            foreach (var header in driver.Options.Headers)
+            {
+                var source = driver.Project.AddFile(header);
+                source.Options = driver.BuildParseOptions(source);
+
+                if (header.Contains ("mini"))
+                    continue;
+
+                source.Options.addDefines ("HAVE_SGEN_GC");
+                source.Options.addDefines ("HAVE_MOVING_COLLECTOR");
+            }
+        }
+
+        static string GetAndroidNdkPath()
+        {
+            // Find the Android NDK's path from Monodroid's config.
+            var configFile = Path.Combine(MonodroidDir, "env.config");
+            if (!File.Exists(configFile))
+                throw new Exception("Expected a valid Monodroid environment config file at " + configFile);
+
+            var config = File.ReadAllText(configFile);
+            var match = Regex.Match(config, @"ANDROID_NDK_PATH\s*:=\s(.*)");
+            return match.Groups[1].Value.Trim();
+        }
+
+        static void ParseCommandLineArgs(string[] args)
+        {
+            var showHelp = false;
+
+            var options = new Mono.Options.OptionSet () {
+                { "abi=", "ABI triple to generate", v => Abis.Add(v) },
+                { "o|out=", "output directory", v => OutputDir = v },
+                { "maccore=", "include directory", v => MaccoreDir = v },
+                { "monodroid=", "include directory", v => MonodroidDir = v },
+                { "mono=", "include directory", v => MonoDir = v },
+                { "h|help",  "show this message and exit",  v => showHelp = v != null },
+            };
+
+            try {
+                options.Parse (args);
+            }
+            catch (Mono.Options.OptionException e) {
+                Console.WriteLine (e.Message);
+                Environment.Exit(0);
+            }
+
+            if (showHelp)
+            {
+                // Print usage and exit.
+                Console.WriteLine("{0} [--abi=triple] [--out=dir] "
+                    + "[--monodroid/maccore=dir] [--mono=dir]",
+                    AppDomain.CurrentDomain.FriendlyName);
+                Environment.Exit(0);
+            }
+        }
+
+        static void Setup(Driver driver, Target target)
+        {
+            var options = driver.Options;
+            options.DryRun = true;
+            options.Verbose = false;
+            options.LibraryName = "Mono";
+            options.MicrosoftMode = false;
+            options.addArguments("-xc");
+            options.addArguments("-std=gnu99");
+            options.addDefines("CPPSHARP");
+
+            foreach (var define in target.Defines)
+                options.addDefines(define);
+
+            SetupToolchainPaths(driver, target);
+
+            SetupMono(options, target);
+        }
+
+        static void SetupMono(DriverOptions options, Target target)
+        {
+            string targetPath;
+            switch (target.Platform) {
+            case TargetPlatform.Android:
+                targetPath = Path.Combine (MonodroidDir, "builds");
+                break;
+            case TargetPlatform.WatchOS:
+            case TargetPlatform.iOS:
+                targetPath = Path.Combine (MaccoreDir, "builds");
+                break;
+            default:
+                throw new ArgumentOutOfRangeException ();
+            }
+
+            if (!Directory.Exists (MonoDir)) {
+                MonoDir = Path.GetFullPath (Path.Combine (targetPath, "../../mono"));
+            }
+
+            var targetBuild = Path.Combine(targetPath, target.Build);
+
+            if (!Directory.Exists(targetBuild))
+                throw new Exception(string.Format("Could not find the target build directory: {0}", targetBuild));
+
+            var includeDirs = new[]
+            {
+                targetBuild,
+                Path.Combine(targetBuild, "eglib", "src"),
+                MonoDir,
+                Path.Combine(MonoDir, "mono"),
+                Path.Combine(MonoDir, "mono", "mini"),
+                Path.Combine(MonoDir, "eglib", "src")
+            };
+
+            foreach (var inc in includeDirs)
+                options.addIncludeDirs(inc);
+
+            var filesToParse = new[]
+            {
+                Path.Combine(MonoDir, "mono", "metadata", "metadata-cross-helpers.c"),
+                Path.Combine(MonoDir, "mono", "mini", "mini-cross-helpers.c"),
+            };
+
+            foreach (var file in filesToParse)
+                options.Headers.Add(file);
+        }
+
+        static void SetupMSVC(Driver driver, string triple)
+        {
+            var options = driver.Options;
+
+            options.Abi = Parser.AST.CppAbi.Microsoft;
+            options.MicrosoftMode = true;
+
+            var systemIncludeDirs = new[]
+            {
+                @"C:\Program Files (x86)\Windows Kits\8.1\Include\um",
+                @"C:\Program Files (x86)\Windows Kits\8.1\Include\shared"
+            };
+
+            foreach (var inc in systemIncludeDirs)
+                options.addSystemIncludeDirs(inc);
+
+            options.addDefines("HOST_WIN32");
+        }
+
+        static void SetupToolchainPaths(Driver driver, Target target)
+        {
+            switch (target.Platform) {
+            case TargetPlatform.Android:
+                SetupAndroidNDK(driver, target);
+                break;
+            case TargetPlatform.iOS:
+            case TargetPlatform.WatchOS:
+                SetupXcode(driver, target);
+                break;
+            default:
+                throw new ArgumentOutOfRangeException ();
+            }
+        }        
+
+        static string GetArchFromTriple(string triple)
+        {
+            if (triple.Contains("mips"))
+                return "mips";
+
+            if (triple.Contains("arm64") || triple.Contains("aarch64"))
+                return "arm64";
+
+            if (triple.Contains("arm"))
+                return "arm";
+
+            if (triple.Contains("i686"))
+                return "x86";
+
+            if (triple.Contains("x86_64"))
+                return "x86_64";
+
+            throw  new Exception("Unknown architecture from triple: " + triple);
+        }
+
+        static string GetXcodeToolchainPath()
+        {
+            var toolchains = Directory.EnumerateDirectories("/Applications", "Xcode*")
+                .ToList();
+            toolchains.Sort();
+
+            var toolchainPath = toolchains.LastOrDefault();
+            if (toolchainPath == null)
+                throw new Exception("Could not find a valid Xcode SDK");
+
+            return toolchainPath;
+        }
+
+        static string GetXcodeBuiltinIncludesFolder()
+        {
+            var toolchainPath = GetXcodeToolchainPath();
+
+            var toolchains = Directory.EnumerateDirectories(Path.Combine(toolchainPath,
+                "Contents/Developer/Toolchains")).ToList();
+            toolchains.Sort();
+
+            toolchainPath = toolchains.LastOrDefault();
+            if (toolchainPath == null)
+                throw new Exception("Could not find a valid Xcode toolchain");
+
+            var includePaths = Directory.EnumerateDirectories(Path.Combine(toolchainPath,
+                "usr/lib/clang")).ToList();
+            var includePath = includePaths.LastOrDefault();
+
+            if (includePath == null)
+                throw new Exception("Could not find a valid Clang include folder");
+
+            return Path.Combine(includePath, "include");
+        }
+
+        static string GetXcodeiOSIncludesFolder()
+        {
+            var toolchainPath = GetXcodeToolchainPath();
+
+            var sdkPaths = Directory.EnumerateDirectories(Path.Combine(toolchainPath,
+                "Contents/Developer/Platforms/iPhoneOS.platform/Developer/SDKs")).ToList();
+            var sdkPath = sdkPaths.LastOrDefault();
+
+            if (sdkPath == null)
+                throw new Exception("Could not find a valid iPhone SDK");
+
+            return Path.Combine(sdkPath, "usr/include");
+        }
+
+        static string GetXcodeWatchOSIncludesFolder()
+        {
+            var toolchainPath = GetXcodeToolchainPath();
+
+            var sdkPaths = Directory.EnumerateDirectories(Path.Combine(toolchainPath,
+                "Contents/Developer/Platforms/WatchOS.platform/Developer/SDKs")).ToList();
+            var sdkPath = sdkPaths.LastOrDefault();
+
+            if (sdkPath == null)
+                throw new Exception("Could not find a valid WatchOS SDK");
+
+            return Path.Combine(sdkPath, "usr/include");
+        }
+
+        static void SetupXcode(Driver driver, Target target)
+        {
+            var options = driver.Options;
+
+            var builtinsPath = GetXcodeBuiltinIncludesFolder();
+            string includePath;
+
+            switch (target.Platform) {
+            case TargetPlatform.iOS:
+                includePath = GetXcodeiOSIncludesFolder();
+                break;
+            case TargetPlatform.WatchOS:
+                includePath = GetXcodeWatchOSIncludesFolder();
+                break;
+            default:
+                throw new ArgumentOutOfRangeException ();
+            }
+
+            options.addSystemIncludeDirs(builtinsPath);
+            options.addSystemIncludeDirs(includePath);
+
+            options.NoBuiltinIncludes = true;
+            options.NoStandardIncludes = true;
+            options.TargetTriple = target.Triple;
+        }
+
+        static string GetAndroidHostToolchainPath()
+        {
+            var androidNdkPath = GetAndroidNdkPath ();
+            var toolchains = Directory.EnumerateDirectories(
+                Path.Combine(androidNdkPath, "toolchains"), "llvm*").ToList();
+            toolchains.Sort();
+
+            var toolchainPath = toolchains.LastOrDefault();
+            if (toolchainPath == null)
+                throw new Exception("Could not find a valid NDK host toolchain");
+
+            toolchains = Directory.EnumerateDirectories(Path.Combine(toolchainPath,
+                "prebuilt")).ToList();
+            toolchains.Sort();
+
+            toolchainPath = toolchains.LastOrDefault();
+            if (toolchainPath == null)
+                throw new Exception("Could not find a valid NDK host toolchain");
+
+            return toolchainPath;
+        }
+
+        static string GetAndroidBuiltinIncludesFolder()
+        {
+            var toolchainPath = GetAndroidHostToolchainPath();
+
+            string clangToolchainPath = Path.Combine(toolchainPath, "lib64", "clang");
+            if (!Directory.Exists (clangToolchainPath))
+                clangToolchainPath = Path.Combine(toolchainPath, "lib", "clang");
+
+            string includePath = null;
+            if (Directory.Exists (clangToolchainPath)) {
+                var includePaths = Directory.EnumerateDirectories(clangToolchainPath).ToList();
+                includePath = includePaths.LastOrDefault();
+            }
+            if (includePath == null)
+                throw new Exception("Could not find a valid Clang include folder");
+
+            return Path.Combine(includePath, "include");
+        }
+
+        static void SetupAndroidNDK(Driver driver, Target target)
+        {
+            var options = driver.Options;
+
+            var builtinsPath = GetAndroidBuiltinIncludesFolder();
+            options.addSystemIncludeDirs(builtinsPath);
+
+            var androidNdkRoot = GetAndroidNdkPath ();
+            const int androidNdkApiLevel = 21;
+
+            var toolchainPath = Path.Combine(androidNdkRoot, "platforms",
+                "android-" + androidNdkApiLevel, "arch-" + GetArchFromTriple(target.Triple),
+                "usr", "include");
+            options.addSystemIncludeDirs(toolchainPath);
+
+            options.NoBuiltinIncludes = true;
+            options.NoStandardIncludes = true;
+            options.TargetTriple = target.Triple;
+        }
+
+        static uint GetTypeAlign(ParserTargetInfo target, ParserIntType type)
+        {
+            switch (type)
+            {
+                case ParserIntType.SignedChar:
+                case ParserIntType.UnsignedChar:
+                    return target.CharAlign;
+                case ParserIntType.SignedShort:
+                case ParserIntType.UnsignedShort:
+                    return target.ShortAlign;
+                case ParserIntType.SignedInt:
+                case ParserIntType.UnsignedInt:
+                    return target.IntAlign;
+                case ParserIntType.SignedLong:
+                case ParserIntType.UnsignedLong:
+                    return target.LongAlign;
+                case ParserIntType.SignedLongLong:
+                case ParserIntType.UnsignedLongLong:
+                    return target.LongLongAlign;
+                default:
+                    throw new Exception("Type has no alignment");
+            }
+        }
+
+        static uint GetTypeSize(ParserTargetInfo target, ParserIntType type)
+        {
+            switch (type)
+            {
+                case ParserIntType.SignedChar:
+                case ParserIntType.UnsignedChar:
+                    return target.CharWidth;
+                case ParserIntType.SignedShort:
+                case ParserIntType.UnsignedShort:
+                    return target.ShortWidth;
+                case ParserIntType.SignedInt:
+                case ParserIntType.UnsignedInt:
+                    return target.IntWidth;
+                case ParserIntType.SignedLong:
+                case ParserIntType.UnsignedLong:
+                    return target.LongWidth;
+                case ParserIntType.SignedLongLong:
+                case ParserIntType.UnsignedLongLong:
+                    return target.LongLongWidth;
+                default:
+                    throw new Exception("Type has no size");
+            }
+        }
+
+        static string GetTargetPlatformDefine(TargetPlatform target)
+        {
+            switch (target) {
+            case TargetPlatform.Android:
+                return "TARGET_ANDROID";
+            case TargetPlatform.iOS:
+                return "TARGET_IOS";
+            case TargetPlatform.WatchOS:
+                return "TARGET_WATCHOS";
+            default:
+                throw new ArgumentOutOfRangeException ();
+            }
+        }
+
+        static void Dump(ASTContext ctx, ParserTargetInfo targetInfo, Target target)
+        {
+            var targetFile = target.Triple;
+
+                       if (!string.IsNullOrEmpty (OutputDir))
+                               targetFile = Path.Combine (OutputDir, targetFile);
+
+            targetFile += ".h";
+
+            using (var writer = new StreamWriter(targetFile))
+            //using (var writer = Console.Out)
+            {
+                writer.WriteLine("#ifndef USED_CROSS_COMPILER_OFFSETS");
+                writer.WriteLine("#ifdef {0}", target.Defines[0]);
+                writer.WriteLine ("#ifdef {0}", GetTargetPlatformDefine (target.Platform));
+                writer.WriteLine("#ifndef HAVE_BOEHM_GC");
+                writer.WriteLine("#define HAS_CROSS_COMPILER_OFFSETS");
+                writer.WriteLine("#if defined (USE_CROSS_COMPILE_OFFSETS) || defined (MONO_CROSS_COMPILE)");
+                writer.WriteLine("#if !defined (DISABLE_METADATA_OFFSETS)");
+                writer.WriteLine("#define USED_CROSS_COMPILER_OFFSETS");
+
+                DumpAligns(writer, targetInfo);
+                DumpSizes(writer, targetInfo);
+                DumpMetadataOffsets(writer, ctx, target);
+
+                writer.WriteLine("#endif //disable metadata check");
+
+                DumpJITOffsets(writer, ctx);
+
+                writer.WriteLine("#endif //cross compiler checks");
+                writer.WriteLine("#endif //gc check");
+                writer.WriteLine("#endif //os check");
+                writer.WriteLine("#endif //arch check");
+                writer.WriteLine("#endif //USED_CROSS_COMPILER_OFFSETS check");
+            }
+
+            Console.WriteLine("Generated offsets file: {0}", targetFile);
+        }
+
+        static void DumpAligns(TextWriter writer, ParserTargetInfo target)
+        {
+            var aligns = new[]
+            {
+                new { Name = "gint8", Align = target.CharAlign},
+                new { Name = "gint16", Align = target.ShortAlign},
+                new { Name = "gint32", Align = target.IntAlign},
+                new { Name = "gint64", Align = GetTypeAlign(target, target.Int64Type)},
+                new { Name = "float", Align = target.FloatAlign},
+                new { Name = "double", Align = target.DoubleAlign},
+                new { Name = "gpointer", Align = GetTypeAlign(target, target.IntPtrType)},
+            };
+
+            // Write the alignment info for the basic types.
+            foreach (var align in aligns)
+                writer.WriteLine("DECL_ALIGN2({0},{1})", align.Name, align.Align / 8);
+        }
+
+        static void DumpSizes(TextWriter writer, ParserTargetInfo target)
+        {
+            var sizes = new[]
+            {
+                new { Name = "gint8", Size = target.CharWidth},
+                new { Name = "gint16", Size = target.ShortWidth},
+                new { Name = "gint32", Size = target.IntWidth},
+                new { Name = "gint64", Size = GetTypeSize(target, target.Int64Type)},
+                new { Name = "float", Size = target.FloatWidth},
+                new { Name = "double", Size = target.DoubleWidth},
+                new { Name = "gpointer", Size = GetTypeSize(target, target.IntPtrType)},
+            };
+
+            // Write the size info for the basic types.
+            foreach (var size in sizes)
+                writer.WriteLine("DECL_SIZE2({0},{1})", size.Name, size.Size / 8);
+        }
+
+        static Class GetClassFromTypedef(ITypedDecl typedef)
+        {
+            var type = typedef.Type.Desugar() as TagType;
+            if (type == null)
+                return null;
+
+            var @class = type.Declaration as Class;
+
+            return @class.IsIncomplete ?
+                (@class.CompleteDeclaration as Class) : @class; 
+        }
+
+        static void DumpClasses(TextWriter writer, ASTContext ctx, IEnumerable<string> types,
+            bool optional = false)
+        {
+            foreach (var @struct in types)
+            {
+                var @class = ctx.FindCompleteClass(@struct);
+                if (@class == null)
+                    @class = ctx.FindCompleteClass("_" + @struct);
+
+                if (@class == null)
+                {
+                    var typedef = ctx.FindTypedef(@struct).FirstOrDefault(
+                        decl => !decl.IsIncomplete);
+
+                    if (typedef != null)
+                        @class = GetClassFromTypedef(typedef);
+                }
+
+                if (@class == null && optional)
+                    continue;
+
+                if (@class == null)
+                    throw new Exception("Expected to find struct definition for " + @struct);
+
+                DumpStruct(writer, @class);
+            }
+        }
+
+        static void DumpMetadataOffsets(TextWriter writer, ASTContext ctx, Target target)
+        {
+            var types = new List<string>
+            {
+                "MonoObject",
+                "MonoClass",
+                "MonoVTable",
+                "MonoDelegate",
+                "MonoInternalThread",
+                "MonoMulticastDelegate",
+                "MonoTransparentProxy",
+                "MonoRealProxy",
+                "MonoRemoteClass",
+                "MonoArray",
+                "MonoArrayBounds",
+                "MonoSafeHandle",
+                "MonoHandleRef",
+                "MonoComInteropProxy",
+                "MonoString",
+                "MonoException",
+                "MonoTypedRef",
+                "MonoThreadsSync",
+                "SgenThreadInfo"
+            };
+
+            DumpClasses(writer, ctx, types);
+        }
+
+        static void DumpJITOffsets(TextWriter writer, ASTContext ctx)
+        {
+            writer.WriteLine("#ifndef DISABLE_JIT_OFFSETS");
+            writer.WriteLine("#define USED_CROSS_COMPILER_OFFSETS");
+
+            var types = new[]
+            {
+                "MonoLMF",
+                "MonoMethodRuntimeGenericContext",
+                "MonoJitTlsData",
+                "MonoGSharedVtMethodRuntimeInfo",
+                "MonoContinuation",
+                "MonoContext",
+                "MonoDelegateTrampInfo",
+            };
+
+            DumpClasses(writer, ctx, types);
+
+            var optionalTypes = new[]
+            {
+                "GSharedVtCallInfo",
+                "SeqPointInfo",
+                "DynCallArgs", 
+                "MonoLMFTramp",
+            };            
+
+            DumpClasses(writer, ctx, optionalTypes, optional: true);
+
+            writer.WriteLine("#endif //disable jit check");
+        }
+
+        static void DumpStruct(TextWriter writer, Class @class)
+        {
+            var name = @class.Name;
+                       if (name.StartsWith ("_", StringComparison.Ordinal))
+                               name = name.Substring (1);
+
+            foreach (var field in @class.Fields)
+            {
+                if (field.IsBitField) continue;
+
+                if (name == "SgenThreadInfo" && field.Name == "regs")
+                    continue;
+
+                writer.WriteLine("DECL_OFFSET2({0},{1},{2})", name, field.Name,
+                    field.Offset / 8);
+            }
+        }
+    }
+}
index 1a9a35eb18ae5136db406fb8c8770e462c39d4e3..2a49fea8b19401abb058883d9ad6fe8b3a2b6d86 100644 (file)
  /* Have signal */
 #define HAVE_SIGNAL 1
 
+ /* Define to 1 if you have the <signal.h> header file. */
+#define HAVE_SIGNAL_H 1
+
 /* Have signbit */
 /* #undef HAVE_SIGNBIT */