edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Initializers.Generated.cs;C806904 File: Initializers.Generated.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Initializers.Generated.cs;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Initializers.Generated.cs;gitpull3 @@ -963,6 +963,10 @@ new System.Func(IronRuby.Builtins.RubyFileOps.AccessTime) ); + module.DefineLibraryMethod("chmod", 0x51, + new System.Func(IronRuby.Builtins.RubyFileOps.Chmod) + ); + module.DefineLibraryMethod("ctime", 0x51, new System.Func(IronRuby.Builtins.RubyFileOps.CreateTime) ); @@ -4344,9 +4348,9 @@ ); module.DefineLibraryMethod("gsub", 0x51, + new System.Func(IronRuby.Builtins.MutableStringOps.ReplaceAll), new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.RubyRegex, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceAll), - new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.MutableString, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceAll), - new System.Func(IronRuby.Builtins.MutableStringOps.ReplaceAll) + new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.MutableString, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceAll) ); module.DefineLibraryMethod("gsub!", 0x51, @@ -4507,9 +4511,9 @@ ); module.DefineLibraryMethod("sub", 0x51, + new System.Func(IronRuby.Builtins.MutableStringOps.ReplaceFirst), new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.RubyRegex, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceFirst), - new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.MutableString, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceFirst), - new System.Func(IronRuby.Builtins.MutableStringOps.ReplaceFirst) + new System.Func, IronRuby.Runtime.RubyScope, IronRuby.Runtime.BlockParam, IronRuby.Builtins.MutableString, IronRuby.Builtins.MutableString, System.Object>(IronRuby.Builtins.MutableStringOps.BlockReplaceFirst) ); module.DefineLibraryMethod("sub!", 0x51, @@ -6881,6 +6885,18 @@ new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipFile.IsClosed) ); + module.DefineLibraryMethod("comment", 0x11, + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipFile.Comment) + ); + + module.DefineLibraryMethod("orig_name", 0x11, + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipFile.OriginalName) + ); + + module.DefineLibraryMethod("original_name", 0x11, + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipFile.OriginalName) + ); + } private static void LoadZlib__GzipFile_Class(IronRuby.Builtins.RubyModule/*!*/ module) { @@ -6897,25 +6913,17 @@ private static void LoadZlib__GzipReader_Instance(IronRuby.Builtins.RubyModule/*!*/ module) { module.DefineLibraryMethod("close", 0x11, - new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Close) + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Close) ); - module.DefineLibraryMethod("comment", 0x11, - new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Comment) - ); - module.DefineLibraryMethod("finish", 0x11, - new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Close) + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Finish) ); module.DefineLibraryMethod("open", 0x12, new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Open) ); - module.DefineLibraryMethod("original_name", 0x11, - new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.OriginalName) - ); - module.DefineLibraryMethod("read", 0x11, new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GZipReader.Read) ); @@ -6941,11 +6949,15 @@ ); module.DefineLibraryMethod("close", 0x11, - new System.Action(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Close) + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Close) ); + module.DefineLibraryMethod("comment=", 0x11, + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Comment) + ); + module.DefineLibraryMethod("finish", 0x11, - new System.Action(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Close) + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Finish) ); module.DefineLibraryMethod("flush", 0x11, @@ -6953,6 +6965,10 @@ new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Flush) ); + module.DefineLibraryMethod("orig_name=", 0x11, + new System.Func(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.OriginalName) + ); + module.DefineLibraryMethod("write", 0x11, new System.Func, IronRuby.Runtime.RubyContext, IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter, IronRuby.Builtins.MutableString, System.Int32>(IronRuby.StandardLibrary.Zlib.Zlib.GzipWriter.Write) ); =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/FileOps.cs;C806880 File: FileOps.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/FileOps.cs;C806880 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/FileOps.cs;gitpull3 @@ -237,10 +237,26 @@ return RubyStatOps.IsCharDevice(RubyStatOps.Create(self.Context, path)); } + private static void Chmod(string path, int permission) { + FileAttributes oldAttributes = File.GetAttributes(path); + if ((permission & 0x80) == 0) { + File.SetAttributes(path, oldAttributes | FileAttributes.ReadOnly); + } else { + File.SetAttributes(path, oldAttributes & ~FileAttributes.ReadOnly); + } + } + + [RubyMethod("chmod")] + public static int Chmod(RubyFile/*!*/ self, [DefaultProtocol]int permission) { + Chmod(self.Path, permission); + return 0; + } + [RubyMethod("chmod", RubyMethodAttributes.PublicSingleton)] - public static int Chmod(RubyClass/*!*/ self, int permission, [DefaultProtocol, NotNull]MutableString/*!*/ path) { + public static int Chmod(RubyClass/*!*/ self, [DefaultProtocol]int permission, [DefaultProtocol, NotNull]MutableString/*!*/ path) { // TODO: implement this correctly for windows - return 0; + Chmod(path.ConvertToString(), permission); + return 1; } //chown @@ -266,6 +282,11 @@ throw new Errno.NoEntryError(String.Format("No such file or directory - {0}", strPath)); } + FileAttributes oldAttributes = File.GetAttributes(strPath); + if ((oldAttributes & FileAttributes.ReadOnly) == FileAttributes.ReadOnly) { + // File.Delete throws UnauthorizedAccessException if the file is read-only + File.SetAttributes(strPath, oldAttributes & ~FileAttributes.ReadOnly); + } File.Delete(strPath); return 1; } @@ -502,20 +523,36 @@ private static MutableString/*!*/ ExpandPath(RubyContext/*!*/ context, MutableString/*!*/ path) { PlatformAdaptationLayer pal = context.DomainManager.Platform; int length = path.Length; + bool raisingRubyException = false; try { if (path == null || length == 0) return Glob.CanonicalizePath(MutableString.Create(Directory.GetCurrentDirectory())); - if (length == 1 && path.GetChar(0) == '~') - return Glob.CanonicalizePath(MutableString.Create(Path.GetFullPath(pal.GetEnvironmentVariable("HOME")))); + if (path.GetChar(0) == '~') { + if (length == 1 || (path.GetChar(1) == Path.DirectorySeparatorChar || + path.GetChar(1) == Path.AltDirectorySeparatorChar)) { - if (path.GetChar(0) == '~' && (path.GetChar(1) == Path.DirectorySeparatorChar || path.GetChar(1) == Path.AltDirectorySeparatorChar)) { - string homeDirectory = pal.GetEnvironmentVariable("HOME"); - return Glob.CanonicalizePath(length < 3 ? MutableString.Create(homeDirectory) : MutableString.Create(Path.Combine(homeDirectory, path.GetSlice(2).ConvertToString()))); + string homeDirectory = pal.GetEnvironmentVariable("HOME"); + if (homeDirectory == null) { + raisingRubyException = true; + throw RubyExceptions.CreateArgumentError("couldn't find HOME environment -- expanding `~'"); + } + if (length <= 2) { + path = MutableString.Create(homeDirectory); + } else { + path = MutableString.Create(Path.Combine(homeDirectory, path.GetSlice(2).ConvertToString())); + } + return Glob.CanonicalizePath(path); + } else { + return path; + } } else { return Glob.CanonicalizePath(MutableString.Create(Path.GetFullPath(path.ConvertToString()))); } } catch (Exception e) { + if (raisingRubyException) { + throw; + } // Re-throw exception as a reasonable Ruby exception throw new Errno.InvalidError(path.ConvertToString(), e); } @@ -563,10 +600,19 @@ return RubyStatOps.IsPipe(RubyStatOps.Create(self.Context, path)); } + private static bool IsReadableImpl(RubyContext/*!*/ context, string/*!*/ path) { + FileSystemInfo fsi; + if (RubyStatOps.TryCreate(context, path, out fsi)) { + return RubyStatOps.IsReadable(fsi); + } else { + return false; + } + } + [RubyMethod("readable?", RubyMethodAttributes.PublicSingleton)] [RubyMethod("readable_real?", RubyMethodAttributes.PublicSingleton)] public static bool IsReadable(RubyClass/*!*/ self, [DefaultProtocol, NotNull]MutableString/*!*/ path) { - return RubyStatOps.IsReadable(RubyStatOps.Create(self.Context, path)); + return IsReadableImpl(self.Context, path.ConvertToString()); } [RubyMethod("readlink", RubyMethodAttributes.PublicSingleton)] =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/Marshal.cs;C806880 File: Marshal.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/Marshal.cs;C806880 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Builtins/Marshal.cs;gitpull3 @@ -283,9 +283,10 @@ } private void WriteRange(Range/*!*/ range) { - _writer.Write((byte)'o'); - WriteSymbol("Range"); + WriteObject(range); WriteInt32(3); + // Write the attributes that are implemented in C#. Any user-defined attributes (for subtypes of Range) + // will be handled by the default handling of IRubyObject WriteSymbol("begin"); WriteAnObject(range.Begin); WriteSymbol("end"); =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Zlib/zlib.cs;C806880 File: zlib.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Zlib/zlib.cs;C806880 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Libraries.LCA_RESTRICTED/Zlib/zlib.cs;gitpull3 @@ -585,6 +585,8 @@ protected int _outPos; protected int _inPos; protected bool _isClosed; + protected MutableString _originalName; + protected MutableString _comment; public GZipFile(IOWrapper/*!*/ ioWrapper) { Debug.Assert(ioWrapper != null); @@ -634,8 +636,12 @@ } } - internal static void Close(UnaryOpStorage/*!*/ closeStorage, GZipFile/*!*/ self) { - if (self._ioWrapper.CanBeClosed) { + internal static void Close(UnaryOpStorage/*!*/ closeStorage, GZipFile/*!*/ self, bool closeIO) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + + if (closeIO && self._ioWrapper.CanBeClosed) { var site = closeStorage.GetCallSite("close"); site.Target(site, self._ioWrapper.UnderlyingObject); } @@ -649,11 +655,29 @@ return self._isClosed; } - // comment() + [RubyMethod("comment")] + public static MutableString Comment(GZipFile/*!*/ self) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + + return self._comment; + } + // crc() // level() // mtime() - // orig_name() + + [RubyMethod("orig_name")] + [RubyMethod("original_name")] + public static MutableString OriginalName(GZipFile/*!*/ self) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + + return self._originalName; + } + // os_code() // sync() // sync = flag @@ -670,8 +694,6 @@ protected MutableString _xtraField; protected MutableString/*!*/ _contents; - protected MutableString/*!*/ _originalName; - protected MutableString/*!*/ _comment; protected ushort _headerCrc; [RubyMethod("xtra_field")] @@ -679,16 +701,6 @@ return self._xtraField; } - [RubyMethod("original_name")] - public static MutableString/*!*/ OriginalName(GZipReader/*!*/ self) { - return self._originalName; - } - - [RubyMethod("comment")] - public static MutableString/*!*/ Comment(GZipReader/*!*/ self) { - return self._comment; - } - [RubyConstant("OSES")] public static string[] OSES = { "FAT filesystem", @@ -836,10 +848,15 @@ } [RubyMethod("close")] + public static object/*!*/ Close(UnaryOpStorage/*!*/ closeStorage, RubyContext/*!*/ context, GZipReader/*!*/ self) { + GZipFile.Close(closeStorage, self, true); + return self._ioWrapper.UnderlyingObject; + } + [RubyMethod("finish")] - public static GZipReader/*!*/ Close(UnaryOpStorage/*!*/ closeStorage, GZipReader/*!*/ self) { - GZipFile.Close(closeStorage, self); - return self; + public static object/*!*/ Finish(UnaryOpStorage/*!*/ closeStorage, RubyContext/*!*/ context, GZipReader/*!*/ self) { + GZipFile.Close(closeStorage, self, false); + return self._ioWrapper.UnderlyingObject; } } @@ -1087,15 +1104,34 @@ } [RubyMethod("close")] + public static object/*!*/ Close(UnaryOpStorage/*!*/ closeStorage, RubyContext/*!*/ context, GzipWriter/*!*/ self) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + self._gzipStream.Close(); + self._ioWrapper.Flush(); + GZipFile.Close(closeStorage, self, true); + return self._ioWrapper.UnderlyingObject; + } + [RubyMethod("finish")] - public static void Close(UnaryOpStorage/*!*/ closeStorage, GzipWriter/*!*/ self) { + public static object/*!*/ Finish(UnaryOpStorage/*!*/ closeStorage, RubyContext/*!*/ context, GzipWriter/*!*/ self) { self._gzipStream.Close(); - self._ioWrapper.Flush(); - GZipFile.Close(closeStorage, self); + self._ioWrapper.Flush(closeStorage, context); + GZipFile.Close(closeStorage, self, false); + return self._ioWrapper.UnderlyingObject; } - // comment=(p1) + [RubyMethod("comment=")] + public static MutableString/*!*/ Comment(GzipWriter/*!*/ self, [NotNull]MutableString/*!*/ comment) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + self._comment = comment; + return comment; + } + [RubyMethod("flush")] public static GzipWriter Flush(UnaryOpStorage/*!*/ flushStorage, RubyContext/*!*/ context, GzipWriter/*!*/ self, object flush) { if (flush != null) { @@ -1123,7 +1159,18 @@ } // mtime=(p1) - // orig_name=(p1) + + [RubyMethod("orig_name=")] + public static MutableString/*!*/ OriginalName(GzipWriter/*!*/ self, [NotNull]MutableString/*!*/ originalName) { + if (self._isClosed) { + throw new Error("closed gzip stream"); + } + + self._originalName = originalName; + + return originalName; + } + // pos() // print(...) // printf(...) =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Builtins/RubyObject.cs;C791094 File: RubyObject.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Builtins/RubyObject.cs;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Builtins/RubyObject.cs;gitpull3 @@ -21,8 +21,15 @@ using IronRuby.Runtime.Calls; using System.Security.Permissions; using IronRuby.Compiler.Generation; +using System.Diagnostics; namespace IronRuby.Builtins { + /// + /// The type to represent user objects that inherit from Object + /// + /// Note that for classes that inherit from some other class, RubyTypeDispenser gets used + /// + [DebuggerDisplay("{ToString()}")] public partial class RubyObject : IRubyObject, IRubyObjectState, IDuplicable, ISerializable { internal const string ClassPropertyName = "Class"; @@ -34,6 +41,15 @@ _class = cls; } + public override string ToString() { +#if DEBUG // This can be made un-conditional after RubyTypeBuilder is also updated to override ToString + UnaryOpStorage unaryOpStorage = new UnaryOpStorage(_class.Context); + return RubyUtils.ObjectToMutableString(unaryOpStorage, this).ConvertToString(); +#else + return base.ToString(); +#endif + } + #if !SILVERLIGHT protected RubyObject(SerializationInfo/*!*/ info, StreamingContext context) { RubyOps.DeserializeObject(out _instanceData, out _class, info); =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Hosting/RubyOptionsParser.cs;C806880 File: RubyOptionsParser.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Hosting/RubyOptionsParser.cs;C806880 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Hosting/RubyOptionsParser.cs;gitpull3 @@ -116,6 +116,7 @@ break; case "-e": + LanguageSetup.Options["MainFile"] = "-e"; if (CommonConsoleOptions.Command == null) { CommonConsoleOptions.Command = String.Empty; } else { =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/RubyContext.cs;C806880 File: RubyContext.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/RubyContext.cs;C806880 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/RubyContext.cs;gitpull3 @@ -61,6 +61,7 @@ private readonly RubyScope/*!*/ _emptyScope; private RubyOptions/*!*/ _options; + private MutableString _commandLineProgramPath; private readonly Loader/*!*/ _loader; private readonly Scope/*!*/ _globalScope; private readonly RubyMetaBinderFactory/*!*/ _metaBinderFactory; @@ -217,6 +218,11 @@ get { return _options; } } + public MutableString CommandLineProgramPath { + get { return _commandLineProgramPath; } + set { _commandLineProgramPath = value; } + } + internal RubyBinder RubyBinder { get { return (RubyBinder)Binder; } } @@ -339,7 +345,9 @@ _globalScope = DomainManager.Globals; _loader = new Loader(this); _emptyScope = new RubyTopLevelScope(this); - + if (_options.MainFile != null) { + _commandLineProgramPath = MutableString.Create(_options.MainFile); + } _currentException = null; _currentSafeLevel = 0; _childProcessExitStatus = null; @@ -399,9 +407,7 @@ // $0 - if (_options.MainFile != null) { - DefineGlobalVariableNoLock(Symbols.CommandLineProgramPath, new GlobalVariableInfo(MutableString.Create(_options.MainFile))); - } + DefineGlobalVariableNoLock("PROGRAM_NAME", Runtime.GlobalVariables.CommandLineProgramPath); DefineGlobalVariableNoLock("stdin", Runtime.GlobalVariables.InputStream); DefineGlobalVariableNoLock("stdout", Runtime.GlobalVariables.OutputStream); =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/GlobalVariables.cs;C791094 File: GlobalVariables.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/GlobalVariables.cs;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/GlobalVariables.cs;gitpull3 @@ -61,6 +61,7 @@ public static readonly GlobalVariable CommandLineArguments = new SpecialGlobalVariableInfo(GlobalVariableId.CommandLineArguments); public static readonly GlobalVariable LastInputLine = new SpecialGlobalVariableInfo(GlobalVariableId.LastInputLine); public static readonly GlobalVariable InputFileName = new SpecialGlobalVariableInfo(GlobalVariableId.InputFileName); + public static readonly GlobalVariable CommandLineProgramPath = new SpecialGlobalVariableInfo(GlobalVariableId.CommandLineProgramPath); public static readonly GlobalVariable InputContent = new SpecialGlobalVariableInfo(GlobalVariableId.InputContent); public static readonly GlobalVariable LastInputLineNumber = new SpecialGlobalVariableInfo(GlobalVariableId.LastInputLineNumber); @@ -75,7 +76,6 @@ public static readonly GlobalVariable OutputStream = new SpecialGlobalVariableInfo(GlobalVariableId.OutputStream); public static readonly GlobalVariable InputStream = new SpecialGlobalVariableInfo(GlobalVariableId.InputStream); public static readonly GlobalVariable ErrorOutputStream = new SpecialGlobalVariableInfo(GlobalVariableId.ErrorOutputStream); - public static readonly GlobalVariable CommandLineProgramPath = new SpecialGlobalVariableInfo(GlobalVariableId.CommandLineProgramPath); public static readonly GlobalVariable SafeLevel = new SpecialGlobalVariableInfo(GlobalVariableId.SafeLevel); public static readonly GlobalVariable Verbose = new SpecialGlobalVariableInfo(GlobalVariableId.Verbose); @@ -99,6 +99,7 @@ context.DefineGlobalVariableNoLock(Symbols.LastInputLine, LastInputLine); // directly accessed variables provided by execution context: + context.DefineGlobalVariableNoLock(Symbols.CommandLineProgramPath, CommandLineProgramPath); context.DefineGlobalVariableNoLock(Symbols.CurrentException, CurrentException); context.DefineGlobalVariableNoLock(Symbols.CurrentExceptionBacktrace, CurrentExceptionBacktrace); context.DefineGlobalVariableNoLock(Symbols.CommandLineArguments, CommandLineArguments); =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/SpecialGlobalVariableInfo.cs;C791094 File: SpecialGlobalVariableInfo.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/SpecialGlobalVariableInfo.cs;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Ruby/Runtime/Globals/SpecialGlobalVariableInfo.cs;gitpull3 @@ -126,6 +126,9 @@ case GlobalVariableId.ChildProcessExitStatus: return context.ChildProcessExitStatus; + case GlobalVariableId.CommandLineProgramPath: + return context.CommandLineProgramPath; + default: throw Assert.Unreachable; } @@ -224,6 +227,10 @@ case GlobalVariableId.Verbose: context.Verbose = value; return; + + case GlobalVariableId.CommandLineProgramPath: + context.CommandLineProgramPath = (value != null) ? RequireType(value, name, "String") : null; + return; case GlobalVariableId.KCode: #if !SILVERLIGHT =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/igem.bat;C791094 File: igem.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/igem.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/igem.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -@"ir.exe" "%~dpn0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iirb.bat;C791094 File: iirb.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iirb.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iirb.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -"%~d0%~p0ir.exe" "%~d0%~p0%~n0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irails.bat;C791094 File: irails.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irails.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irails.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -@"ir.exe" "%~dpn0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irake.bat;C791094 File: irake.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irake.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irake.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -@"ir.exe" "%~dpn0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irdoc.bat;C791094 File: irdoc.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irdoc.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/irdoc.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -"%~d0%~p0ir.exe" "%~d0%~p0%~n0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iri.bat;C791094 File: iri.bat =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iri.bat;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Scripts/bin/iri.bat;gitpull3 @@ -1,2 +1,10 @@ -@ECHO OFF -"%~d0%~p0ir.exe" "%~d0%~p0%~n0" %* +@echo off +setlocal + +set IR_CMD="%~dp0ir.exe" +if defined MERLIN_ROOT ( + REM - This is a dev environment. See http://wiki.github.com/ironruby/ironruby + set IR_CMD="%MERLIN_ROOT%\bin\Debug\ir.exe" +) + +%IR_CMD% "%~dpn0" %* =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fields edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fixtures.generated.cs;C806904 File: fixtures.generated.cs =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fixtures.generated.cs;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fixtures.generated.cs;gitpull3 @@ -1,15 +1,38 @@ +using Microsoft.Scripting.Hosting; + using IronRuby.Runtime; + using IronRuby.Builtins; #line 4 "./bcl/array/conversion_spec.rb" public partial class Klass { public T[] ArrayAcceptingMethod(T[] arg0) { return arg0; } } +#line 4 "./bcl/numerics/decimal_spec.rb" +public partial class Klass { + public decimal MyDecimal {get; set;} + } #line 14 "./class/instantiation/abstract_spec.rb" public partial class DerivedFromAbstract : AbstractClass { public override int m() {return 1;} } #line 32 "./class/instantiation/abstract_spec.rb" public abstract partial class AbstractDerived : Klass {} +#line 9 "./class/instantiation/class_spec.rb" +public partial class OverloadedConstructorClass { + public string val; + + public OverloadedConstructorClass() { + val = "empty constructor"; + } + + public OverloadedConstructorClass(string str) { + val = "string constructor"; + } + + public OverloadedConstructorClass(string str, int i) { + val = "string int constructor"; + } + } #line 4 "./class/mapping_spec.rb" public class EmptyClass {} public partial class Klass {public int m() {return 1;}} @@ -23,10 +46,73 @@ public class GenericClass{public int m() {return 1;}} public class EmptyGeneric2Class{} public class Generic2Class{public int m() {return 1;}} +#line 10 "./delegate/conversion_spec.rb" +#line 15 "./delegate/conversion_spec.rb" +public partial class DelegateConversionClass { + public delegate int Delegate1(string str); + private ScriptEngine _engine; + private Proc _lambda; + + public DelegateConversionClass(string lambdaExpr) { + _engine = IronRuby.Ruby.CreateEngine(); + _lambda = (Proc) _engine.Execute(lambdaExpr); + } + + public int DirectInvoke() { + return (int) _engine.Operations.Invoke(_lambda, "1"); + } + + public int ConvertToDelegate() { + Delegate1 d = _engine.Operations.ConvertTo(_lambda); + return d("1"); + } + } #line 4 "./delegate/mapping_spec.rb" public delegate void VoidVoidDelegate(); #line 4 "./enum/mapping_spec.rb" public enum EnumInt : int { A, B, C} +#line 4 "./events/invocation_spec.rb" +public class ClassWithEvents { + public event EventHandler FullEvent; + public static event EventHandler StaticFullEvent; + + public void InvokeFullEvent(int count) { + if (FullEvent != null) FullEvent(this, count); + } + + public static void InvokeStaticFullEvent(int count) { + if (StaticFullEvent != null) StaticFullEvent(new object(), count); + } + } +#line 15 "./events/mapping_spec.rb" +#pragma warning disable 67 + public delegate void EventHandler(object source, int count); + public partial class BasicEventClass { + public event EventHandler OnEvent; + } + #pragma warning restore 67 +#line 4 "./fields/access_spec.rb" +#pragma warning disable 414 + public partial class ClassWithFields { + public string field = "field"; + public const string constField = "const"; + public readonly string readOnlyField = "readonly"; + public static string staticField = "static"; + public static readonly string staticReadOnlyField = "static readonly"; + + private string privateField = "private field"; + private const string privateConstField = "private const"; + private readonly string privateReadOnlyField = "private readonly"; + private static string privateStaticField = "private static"; + private static readonly string privateStaticReadOnlyField = "private static readonly"; + + protected string protectedField = "protected field"; + protected const string protectedConstField = "protected const"; + protected readonly string protectedReadOnlyField = "protected readonly"; + protected static string protectedStaticField = "protected static"; + protected static readonly string protectedStaticReadOnlyField = "protected static readonly"; + } + #pragma warning restore 414 #line 4 "./interface/mapping_spec.rb" public interface IEmptyInterface {} public interface IInterface { void m();} @@ -421,6 +507,25 @@ } #pragma warning restore 693 +#line 4 "./method/invocation/indexers_spec.rb" +public partial class ClassWithIndexer { + public int[,] Values = new int[,] { {0, 10}, {20, 30} }; + + public int this[int i, int j] { + get { return Values[i,j]; } + set { Values[i,j] = value; } + } + } +#line 4 "./method/invocation/overload_spec.rb" +public partial class ClassWithOverloads { + public string PublicProtectedOverload(){ + return "public overload"; + } + + protected string PublicProtectedOverload(string str) { + return "protected overload"; + } + } #line 4 "./method/modification/override_spec.rb" public partial class ClassWithMethods { public int SummingMethod(int a, int b){ =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fixtures.generated.dll;C806904 fixtures.generated.dll: files differ edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/matchers.rb;C791094 File: matchers.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/matchers.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/matchers.rb;gitpull3 @@ -41,8 +41,31 @@ end end +class ClrStringMatcher + def initialize(str) + @expected = str + end + + def matches?(actual) + @actual = actual + @actual.to_s == @expected + end + + def failure_message + ["Expected CLR string '#{@actual}'", "to equal Ruby string \"#{@expected}\""] + end + + def negative_failure_message + ["Expected CLR string '#{@actual}'", "to not equal Ruby string \"#{@expected}\""] + end +end + class Object def be_able_to_load(assembly) BeAbleToLoadMatcher.new(assembly) end + + def equal_clr_string(str) + ClrStringMatcher.new(str) + end end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/spec_helper.rb;C806904 File: spec_helper.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/spec_helper.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/spec_helper.rb;gitpull3 @@ -54,6 +54,8 @@ class Object def csc(*args) end + def reference(arg) + end def assembly(*args) yield end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/test_basic.rb;C802353 File: test_basic.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/test_basic.rb;C802353 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/test_basic.rb;gitpull3 @@ -11,103 +11,14 @@ # You must not remove this notice, or any other, from this software. # # -# **************************************************************************** - +# **************************************************************************** + require "../util/assert.rb" require "mscorlib" -def test_stringbuilder - x = System::Text::StringBuilder.new - x.Append("abc") - x.Append("def") - x.Append(100) - x.Insert(3, "012") - - assert_equal(x.ToString, System::String::Concat("abc012def100")) - - x.Capacity = 20 - assert_equal(x.Capacity, 20) - assert_equal(x.Length, 12) -end -def test_string - a = System::Char::Parse("a") - b = System::Char::Parse("b") - x = System::String.new(a, 2) - y = System::String.new(b, 3) - - str = System::String - assert_equal(str.Concat(x, y), System::String::Concat("aabbb")) - - assert_equal(str.Compare(x, y), -1) - assert_equal(str.Compare(y, x), 1) - assert_equal(str.Compare(x, x), 0) -end -def test_field - # const field - assert_equal(System::Int32.MaxValue, 2147483647) - # enum - assert_equal(System::DayOfWeek.Sunday.ToString().to_str, 'Sunday') - # readonly field - assert_equal(System::DateTime.MaxValue.ToString().to_str, '12/31/9999 11:59:59 PM') - - assert_raise(NoMethodError) { print System::Int32.MaxValue2 } - - # setting to a read only field raises NoMethodError - assert_raise(NoMethodError) { System::Int32.MaxValue = 5 } - assert_raise(NoMethodError) { System::DayOfWeek.Sunday = 5 } - assert_raise(NoMethodError) { System::DateTime.MaxValue = 5 } - - # TODO: set field test (need a type with a writable static field) -end - -def test_event - require "System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" - - t = System::Timers::Timer.new(1000) - $flag = 0 - t.Elapsed do |sender, e| - $flag += 1 - sender.Enabled = false - end - t.Enabled = true - t.Start() - System::Threading::Thread.Sleep(3000) - t.Stop() - assert_equal($flag, 1) -end - -def test_generictypes - # TODO: more interesting tests when more features of .NET interop are working - list = System::Collections::Generic::List - - IntList = list.of(System::Int32) - a = IntList.new - a.add 1 - a.add 2 - a.add 3 - assert_equal(a.count, 3) - - IntList2 = list[Fixnum] - assert_equal(IntList2.new.to_string, 'System.Collections.Generic.List`1[System.Int32]'.to_clr_string) - - Dict = System::Collections::Generic::Dictionary[System::String, System::String] - assert_equal(Dict.new.to_string, 'System.Collections.Generic.Dictionary`2[System.String,System.String]'.to_clr_string) - - assert_raise(ArgumentError) { System::Type.of(Fixnum) } - assert_raise(ArgumentError) { list[System] } - assert_raise(ArgumentError) { list[1] } - assert_raise(ArgumentError) { list[] } - assert_raise(ArgumentError) { list.of(Fixnum, Fixnum) } - - #System::Nullable.of(System::Int32) - #System::IComparable.of(Fixnum) - System::Predicate.of(System::Int32) -end - - def test_ienumerable # .NET types that implement IEnumerable should # implement each & include Enumerable @@ -258,11 +169,6 @@ end end -test_event -test_field -test_string -test_stringbuilder -test_generictypes test_ienumerable # TODO: disabling this test until we figure out how to enable creating DateTime # objects using their ctors and not Time's RubyConstructors =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/A/a.generated.dll;C806904 a.generated.dll: files differ edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/B/b.generated.dll;C806904 b.generated.dll: files differ add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/numerics add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/string edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/array/instantiation_spec.rb;C806904 File: instantiation_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/array/instantiation_spec.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/array/instantiation_spec.rb;gitpull3 @@ -28,7 +28,7 @@ end it "can be done with multi-dimnsion arrays via create_instance" do - @array.class.to_s.should == "System::Int32[,]" + @array.class.should equal_clr_string("System::Int32[,]") end it "can be referenced" do =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/numerics/decimal_spec.rb File: decimal_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/numerics/decimal_spec.rb;gitpull3 @@ -1,0 +1,18 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "C# decimal numbers" do + csc <<-EOL + public partial class Klass { + public decimal MyDecimal {get; set;} + } + EOL + it "should be able to check as equal to Float" do + #regression test for [#19872] IComparableOps.CompareTo + #throws argument error when type is Decimal + klass = Klass.new + klass.my_decimal = 10 + klass.my_decimal.should == 10 + klass.my_decimal = 1.0 + klass.my_decimal.should == 1.0 + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/string/string_spec.rb File: string_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/string/string_spec.rb;gitpull3 @@ -1,0 +1,22 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "System::String" do + before :each do + @a = System::Char::Parse("a") + @b = System::Char::Parse("b") + @aa = System::String.new(@a, 2) + @bbb = System::String.new(@b, 3) + @str = System::String + end + + it "can be parsed" do + @a.should equal_clr_string("a") + end + + it "can have it's methods used" do + @str.concat(@aa, @bbb).should equal_clr_string("aabbb") + @str.compare(@aa, @bbb).should == -1 + @str.compare(@bbb, @aa).should == 1 + @str.compare(@aa, @aa).should == 0 + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/string/stringbuilder_spec.rb File: stringbuilder_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/bcl/string/stringbuilder_spec.rb;gitpull3 @@ -1,0 +1,17 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "System::Text::StringBuilder" do + it "creates a .NET StringBuilder object" do + str = System::Text::StringBuilder.new + str.append("abc") + str.append("def") + str.append(100) + str.insert(3, "012") + + str.to_string.should equal_clr_string("abc012def100") + + str.capacity = 20 + str.capacity.should == 20 + str.length.should == 12 + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/class/instantiation/class_spec.rb File: class_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/class/instantiation/class_spec.rb;gitpull3 @@ -1,0 +1,44 @@ +require File.dirname(__FILE__) + '/../../spec_helper' +require File.dirname(__FILE__) + '/../shared/instantiable' + +describe "General .NET classes" do + it_behaves_like :instantiable_class, Klass +end + +describe "Ruby classes derived from .NET classes with overloaded constructors" do + csc <<-EOL + public partial class OverloadedConstructorClass { + public string val; + + public OverloadedConstructorClass() { + val = "empty constructor"; + } + + public OverloadedConstructorClass(string str) { + val = "string constructor"; + } + + public OverloadedConstructorClass(string str, int i) { + val = "string int constructor"; + } + } + EOL + class RubyOverloadedConstructorClass < OverloadedConstructorClass + def initialize(val) + super val + end + end + + it_behaves_like :instantiable_class, OverloadedConstructorClass + + it "properly selects overloaded constructors" do + OverloadedConstructorClass.new("hello").should be_kind_of(OverloadedConstructorClass) + OverloadedConstructorClass.new("hello").val.should equal_clr_string("string constructor") + end + + it "properly selects overloaded constructors for super" do + RubyOverloadedConstructorClass.new("hello").should be_kind_of(RubyOverloadedConstructorClass) + OverloadedConstructorClass.new("hello").val.should equal_clr_string("string constructor") +end + +end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/class/instantiation/generic_spec.rb;C806904 File: generic_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/class/instantiation/generic_spec.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/class/instantiation/generic_spec.rb;gitpull3 @@ -8,6 +8,10 @@ describe "Generic .NET classes with type param" do it_behaves_like :instantiable_class, GenericClass[Object] + + describe "of interface" do + it_behaves_like :instantiable_class, GenericClass[IInterface] + end end describe "Empty generic .NET classes" do @@ -16,6 +20,10 @@ describe "Empty generic .NET classes with type param" do it_behaves_like :instantiable_class, EmptyGenericClass[Object] + + describe "of interface" do + it_behaves_like :instantiable_class, EmptyGenericClass[IInterface] + end end describe "Generic .NET classes with 2 params" do =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/delegate/conversion_spec.rb File: conversion_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/delegate/conversion_spec.rb;gitpull3 @@ -1,0 +1,48 @@ +require File.dirname(__FILE__) + '/../spec_helper' + +describe "Converting procs to delegates" do + bin = "#{ENV['MERLIN_ROOT']}\\bin\\debug" + reference "#{bin}\\Microsoft.Scripting.ExtensionAttribute.dll" + reference "#{bin}\\Microsoft.Scripting.dll" + reference "#{bin}\\Microsoft.Scripting.Core.dll" + reference "#{bin}\\IronRuby.dll" + reference "#{bin}\\IronRuby.Libraries.dll" + csc <<-EOL + using Microsoft.Scripting.Hosting; + using IronRuby.Runtime; + using IronRuby.Builtins; + EOL + csc <<-EOL + public partial class DelegateConversionClass { + public delegate int Delegate1(string str); + private ScriptEngine _engine; + private Proc _lambda; + + public DelegateConversionClass(string lambdaExpr) { + _engine = IronRuby.Ruby.CreateEngine(); + _lambda = (Proc) _engine.Execute(lambdaExpr); + } + + public int DirectInvoke() { + return (int) _engine.Operations.Invoke(_lambda, "1"); + } + + public int ConvertToDelegate() { + Delegate1 d = _engine.Operations.ConvertTo(_lambda); + return d("1"); + } + } + EOL + before :each do + @klass = DelegateConversionClass.new("lambda {|a| a.to_i}") + end + + #TODO: does this belong somewhere else? + it "can directly invoke a lambda" do + @klass.direct_invoke.should == 1 + end + + it "can convert to a lambda" do + @klass.convert_to_delegate.should == 1 + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/invocation_spec.rb File: invocation_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/invocation_spec.rb;gitpull3 @@ -1,0 +1,144 @@ +require File.dirname(__FILE__) + '/../spec_helper' + +describe "Invoking events" do + csc <<-EOL + public class ClassWithEvents { + public event EventHandler FullEvent; + public static event EventHandler StaticFullEvent; + + public void InvokeFullEvent(int count) { + if (FullEvent != null) FullEvent(this, count); + } + + public static void InvokeStaticFullEvent(int count) { + if (StaticFullEvent != null) StaticFullEvent(new object(), count); + } + } + EOL + class EventHandlerHelper + def initialize + @store = Hash.new(0) + end + + def foo(s, count) + @store[:method] += count + end + + def [](key) + @store[key] + end + + def []=(key, value) + @store[key] = value + end + end + + before :each do + @helper = EventHandlerHelper.new + @method = @helper.method(:foo) + @lambda = lambda { |s, count| @helper[:lambda] += count } + @proc = proc { |s, count| @helper[:proc] += count } + @klass = ClassWithEvents.new + @no_event_klass = ClassWithEvents.new + end + + it "works with methods via add" do + @klass.full_event.add @method + @klass.invoke_full_event(1) + @helper[:method].should == 1 + end + + it "works with methods via +=" do + @klass.full_event += @method + @klass.invoke_full_event(1) + @helper[:method].should == 1 + end + + it "works with lambdas via add" do + @klass.full_event.add @lambda + @klass.invoke_full_event(1) + @helper[:lambda].should == 1 + end + + it "works with methods via +=" do + @klass.full_event += @lambda + @klass.invoke_full_event(1) + @helper[:lambda].should == 1 + end + + it "works with procs via add" do + @klass.full_event.add @proc + @klass.invoke_full_event(1) + @helper[:proc].should == 1 + end + + it "works with methods via +=" do + @klass.full_event += @proc + @klass.invoke_full_event(1) + @helper[:proc].should == 1 + end + + it "works with to_proc syntax" do + @klass.full_event &@lambda + @klass.invoke_full_event(1) + @helper[:lambda].should == 1 + end + + it "works with block syntax" do + @klass.full_event {|s,e| @helper[:block] += e} + @klass.invoke_full_event(1) + @helper[:block].should == 1 + end + + it "works with multiple objects via add" do + @klass.full_event.add @method + @klass.full_event.add @proc + @klass.full_event.add @lambda + @klass.invoke_full_event(1) + @helper[:proc].should == 1 + @helper[:method].should == 1 + @helper[:lambda].should == 1 + end + + it "works with multiple objects via +=" do + @klass.full_event += @method + @klass.full_event += @proc + @klass.full_event += @lambda + @klass.invoke_full_event(1) + @helper[:proc].should == 1 + @helper[:method].should == 1 + @helper[:lambda].should == 1 + end + + it "works with multiple of one callback via add" do + @klass.full_event.add @method + @klass.full_event.add @method + @klass.invoke_full_event(1) + @helper[:method].should == 2 + end + + it "works with multiple of one callback via +=" do + @klass.full_event += @method + @klass.full_event += @method + @klass.invoke_full_event(1) + @helper[:method].should == 2 + end + + it "registers adds and removes" do + @klass.full_event.add @method + @klass.full_event.add @method + @klass.invoke_full_event(1) + @klass.full_event.remove @method + @klass.invoke_full_event(1) + @helper[:method].should == 3 + end + + it "registers adds and removes" do + @klass.full_event += @method + @klass.full_event += @method + @klass.invoke_full_event(1) + @klass.full_event -= @method + @klass.invoke_full_event(1) + @helper[:method].should == 3 + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/mapping_spec.rb File: mapping_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/mapping_spec.rb;gitpull3 @@ -1,0 +1,26 @@ +require File.dirname(__FILE__) + '/../spec_helper' + +describe ".NET events" do + before :all do + Foo = IronRuby + Object.send :remove_const, :IronRuby + require "IronRuby, Version=0.3.0.0, Culture=neutral, PublicKeyToken=null" + end + + after :all do + verb, $VERBOSE = $VERBOSE, nil + IronRuby = Foo + $VERBOSE = verb + end + csc <<-EOL + #pragma warning disable 67 + public delegate void EventHandler(object source, int count); + public partial class BasicEventClass { + public event EventHandler OnEvent; + } + #pragma warning restore 67 + EOL + it "map to a custom class" do + BasicEventClass.new.on_event.should be_kind_of IronRuby::Builtins::RubyEvent + end +end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/modification add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/modification/adding_spec.rb File: adding_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/modification/adding_spec.rb;gitpull3 @@ -1,0 +1,68 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "Basic .NET events allow adding" do + before :each do + def foo(s,e); end + @method = method(:foo) + @lambda = lambda {|a,b| } + @proc = proc {|a,b| } + + @klass = BasicEventClass.new + end + + it "method handlers via add" do + lambda{ @klass.OnEvent.add @method }.should_not raise_error + end + + it "method handlers via +=" do + lambda{ @klass.on_event += @method }.should_not raise_error + end + + it "lambda's via add" do + lambda{ @klass.on_event.add @lambda }.should_not raise_error + end + + it "lambda's via +=" do + lambda{ @klass.on_event += @lambda }.should_not raise_error + end + + it "procs via add" do + lambda{ @klass.on_event.add @proc }.should_not raise_error + end + + it "procs via +=" do + lambda{ @klass.on_event += @proc }.should_not raise_error + end + + it "multiple items via add" do + lambda do + @klass.on_event.add @method + @klass.on_event.add @proc + @klass.on_event.add @lambda + end.should_not raise_error + end + + it "multiple items via +=" do + lambda do + @klass.on_event += @method + @klass.on_event += @proc + @klass.on_event += @lambda + end.should_not raise_error + end + + it "one item multiple times via add" do + lambda do + @klass.on_event.add @method + @klass.on_event.add @method + end.should_not raise_error + end + + it "one item multiple times via +=" do + lambda do + @klass.on_event += @method + @klass.on_event += @method + end.should_not raise_error + end +end + + =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/modification/removal_spec.rb File: removal_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/events/modification/removal_spec.rb;gitpull3 @@ -1,0 +1,88 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "Basic .NET events allow removing" do + before :each do + def foo(s,e); end + @method = method(:foo) + @lambda = lambda {|a,b| } + @proc = proc {|a,b| } + + @klass = BasicEventClass.new + @klass.on_event.add @method + @klass.on_event.add @method + @klass.on_event.add @lambda + @klass.on_event.add @proc + end + + it "method handlers via remove" do + lambda{ @klass.OnEvent.remove @method }.should_not raise_error + end + + it "method handlers via -=" do + lambda{ @klass.on_event -= @method }.should_not raise_error + end + + it "lambda's via remove" do + lambda{ @klass.on_event.remove @lambda }.should_not raise_error + end + + it "lambda's via -=" do + lambda{ @klass.on_event -= @lambda }.should_not raise_error + end + + it "procs via remove" do + lambda{ @klass.on_event.remove @proc }.should_not raise_error + end + + it "procs via -=" do + lambda{ @klass.on_event -= @proc }.should_not raise_error + end + + it "multiple items via remove" do + lambda do + @klass.on_event.remove @method + @klass.on_event.remove @proc + @klass.on_event.remove @lambda + end.should_not raise_error + end + + it "multiple items via -=" do + lambda do + @klass.on_event -= @method + @klass.on_event -= @proc + @klass.on_event -= @lambda + end.should_not raise_error + end + + it "one item multiple times via remove" do + lambda do + @klass.on_event.remove @method + @klass.on_event.remove @method + end.should_not raise_error + end + + it "one item multiple times via -=" do + lambda do + @klass.on_event -= @method + @klass.on_event -= @method + end.should_not raise_error + end + + it "one item more times than it is in the list via remove" do + lambda do + @klass.on_event.remove @method + @klass.on_event.remove @method + @klass.on_event.remove @method + end.should_not raise_error + end + + it "one item more times than it is in the list via -=" do + lambda do + @klass.on_event -= @method + @klass.on_event -= @method + @klass.on_event -= @method + end.should_not raise_error + end +end + + =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fields/access_spec.rb File: access_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/fields/access_spec.rb;gitpull3 @@ -1,0 +1,179 @@ +require File.dirname(__FILE__) + '/../spec_helper' + +describe "Reading .NET Fields" do + csc <<-EOL + #pragma warning disable 414 + public partial class ClassWithFields { + public string field = "field"; + public const string constField = "const"; + public readonly string readOnlyField = "readonly"; + public static string staticField = "static"; + public static readonly string staticReadOnlyField = "static readonly"; + + private string privateField = "private field"; + private const string privateConstField = "private const"; + private readonly string privateReadOnlyField = "private readonly"; + private static string privateStaticField = "private static"; + private static readonly string privateStaticReadOnlyField = "private static readonly"; + + protected string protectedField = "protected field"; + protected const string protectedConstField = "protected const"; + protected readonly string protectedReadOnlyField = "protected readonly"; + protected static string protectedStaticField = "protected static"; + protected static readonly string protectedStaticReadOnlyField = "protected static readonly"; + } + #pragma warning restore 414 + EOL + before :each do + @klass = ClassWithFields.new + end + + describe "works with public" do + it "fields" do + @klass.field.should equal_clr_string("field") + end + + it "const fields" do + ClassWithFields.constField.should equal_clr_string("const") + end + + it "readonly fields" do + @klass.readOnlyField.should equal_clr_string("readonly") + end + + it "static fields" do + ClassWithFields.staticField.should equal_clr_string("static") + end + + it "static readonly fields" do + ClassWithFields.staticReadOnlyField.should equal_clr_string("static readonly") + end + end + + describe "works with protected" do + it "fields" do + @klass.protectedField.should equal_clr_string("protected field") + end + + it "const fields" do + ClassWithFields.protectedConstField.should equal_clr_string("protected const") + end + + it "readonly fields" do + @klass.protectedReadOnlyField.should equal_clr_string("protected readonly") + end + + it "static fields" do + ClassWithFields.protectedStaticField.should equal_clr_string("protected static") + end + + it "static readonly fields" do + ClassWithFields.protectedStaticReadOnlyField.should equal_clr_string("protected static readonly") + end + end + + if IronRuby.dlr_config.private_binding + describe "works with private" do + it "fields" do + @klass.privateField.should equal_clr_string("private field") + end + + it "const fields" do + @klass.privateConstField.should equal_clr_string("private const") + end + + it "readonly fields" do + @klass.privateReadOnlyField.should equal_clr_string("private readonly") + end + + it "static fields" do + ClassWithFields.privateStaticField.should equal_clr_string("private static") + end + + it "static readonly fields" do + ClassWithFields.privateStaticReadOnlyField.should equal_clr_string("private static readonly") + end + end + end +end + +describe "Setting .NET Fields" do + before :each do + @klass = ClassWithFields.new + end + + describe "with public" do + it "fields works" do + @klass.field = "bar" + @klass.field.should equal_clr_string("bar") + end + + it "const fields raises NoMethodError" do + lambda {ClassWithFields.constField = "foo"}.should raise_error(NoMethodError) + end + + it "readonly fields" do + lambda {ClassWithFields.readOnlyField = "foo"}.should raise_error(NoMethodError) + end + + it "static fields" do + ClassWithFields.staticField = "foo" + ClassWithFields.staticField.should equal_clr_string("foo") + end + + it "static readonly fields" do + lambda {ClassWithFields.staticReadOnlyField = "foo"}.should raise_error(NoMethodError) + end + end + + describe "with protected" do + it "fields works" do + @klass.protectedField = "bar" + @klass.protectedField.should equal_clr_string("bar") + end + + it "const fields raises NoMethodError" do + lambda {ClassWithFields.protectedConstField = "foo"}.should raise_error(NoMethodError) + end + + it "readonly fields" do + lambda {ClassWithFields.protectedReadOnlyField = "foo"}.should raise_error(NoMethodError) + end + + it "static fields" do + ClassWithFields.protectedStaticField = "foo" + ClassWithFields.protectedStaticField.should equal_clr_string("foo") + end + + it "static readonly fields" do + lambda {ClassWithFields.protectedStaticReadOnlyField = "foo"}.should raise_error(NoMethodError) + end + end + + if IronRuby.dlr_config.private_binding + describe "with private" do + it "fields works" do + @klass.privateField = "bar" + @klass.privateField.should equal_clr_string("bar") + end + + it "const fields raises NoMethodError" do + lambda {ClassWithFields.privateConstField = "foo"}.should raise_error(NoMethodError) + end + + it "readonly fields" do + lambda {ClassWithFields.privateReadOnlyField = "foo"}.should raise_error(NoMethodError) + end + + it "static fields" do + ClassWithFields.privateStaticField = "foo" + ClassWithFields.privateStaticField.should equal_clr_string("foo") + end + + it "static readonly fields" do + lambda {ClassWithFields.privateStaticReadOnlyField = "foo"}.should raise_error(NoMethodError) + end + end + end +end + =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/interface/mapping_spec.rb;C791094 File: mapping_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/interface/mapping_spec.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/interface/mapping_spec.rb;gitpull3 @@ -8,6 +8,12 @@ it "map to modules" do [IEmptyInterface, IInterface].each do |iface| iface.should be_kind_of Module + iface.should_not be_kind_of Class end end + + it "map to modules when a concrete instance of a generic interface" do + System::IEquatable.of(Fixnum).should be_kind_of Module + System::IEquatable.of(Fixnum).should_not be_kind_of Class + end end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/reflection_spec.rb;C806904 File: reflection_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/reflection_spec.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/reflection_spec.rb;gitpull3 @@ -72,15 +72,15 @@ end it "can be called" do - @meth.call.to_s.should == "public" - @meth[].to_s.should == "public" + @meth.call.should equal_clr_string("public") + @meth[].should equal_clr_string("public") end it "can be unbound" do m = @meth.unbind m.should be_kind_of UnboundMethod m = m.bind(ClassWithMethods.new) - m.call.to_s.should == "public" + m.call.should equal_clr_string("public") end end @@ -99,7 +99,7 @@ it "act as a single Ruby method" do @methods.should be_kind_of Method - @methods.call.to_s.should == "empty" + @methods.call.should equal_clr_string("empty") end it "contain .NET method objects" do =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/generic_spec.rb;C806904 File: generic_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/generic_spec.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/generic_spec.rb;gitpull3 @@ -125,15 +125,15 @@ EOL describe :generic_methods, :shared => true do it "are callable via call and [] when pubic or protected" do - @klass.method(:public_1_generic_0_arg).of(Fixnum).call.to_s.should == "public generic no args" + @klass.method(:public_1_generic_0_arg).of(Fixnum).call.should equal_clr_string("public generic no args") (@public_method_list + @protected_method_list).each do |m| generic_count, arity = m.match(/_(\d)_generic_(\d)_/)[1..2].map {|e| e.to_i} generics = Array.new(generic_count, Fixnum) args = Array.new(arity, 1) args << args.pop.to_s.to_clr_string if arity > generic_count - @klass.method(m).of(*generics).call(*args).to_s.should == args.join(" ") - @klass.method(m).of(*generics)[*args].to_s.should == args.join(" ") + @klass.method(m).of(*generics).call(*args).should equal_clr_string(args.join(" ")) + @klass.method(m).of(*generics)[*args].should equal_clr_string(args.join(" ")) end end @@ -161,8 +161,8 @@ args = Array.new(arity, 1) args << args.pop.to_s.to_clr_string if arity > generic_count - @klass.method(m).of(*generics).call(*args).to_s.should == args.join(" ") - @klass.method(m).of(*generics)[*args].to_s.should == args.join(" ") + @klass.method(m).of(*generics).call(*args).should equal_clr_string(args.join(" ")) + @klass.method(m).of(*generics)[*args].should equal_clr_string(args.join(" ")) end end end @@ -208,11 +208,11 @@ describe :generic_conflicting_methods, :shared => true do it "binds class type parameter correctly" do - @klass.method(:public_1_generic_2_arg).of(String).call("hello", 1).to_s.should == "hello 1" + @klass.method(:public_1_generic_2_arg).of(String).call("hello", 1).should equal_clr_string("hello 1") end it "binds conflicting type parameter correctly" do - @klass.method(:conflicting_generic_method).of(String).call("hello").to_s.should == "hello" + @klass.method(:conflicting_generic_method).of(String).call("hello").should equal_clr_string("hello") end end describe "Generic methods" do =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/indexers_spec.rb File: indexers_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/indexers_spec.rb;gitpull3 @@ -1,0 +1,31 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "Calling indexers" do + csc <<-EOL + public partial class ClassWithIndexer { + public int[,] Values = new int[,] { {0, 10}, {20, 30} }; + + public int this[int i, int j] { + get { return Values[i,j]; } + set { Values[i,j] = value; } + } + } + EOL + before :each do + @klass = ClassWithIndexer.new + end + + it "can be done on set indexers" do + @klass[0,0] = 1 + @klass.Values[0,0].should == 1 + end + + it "can be done on get indexers" do + @klass[0,1].should == 10 + end + + it "properly respect type" do + lambda { @klass["string",1] }.should raise_error TypeError + lambda { @klass[1,"string"] }.should raise_error TypeError + end +end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/overload_spec.rb;C791094 File: overload_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/overload_spec.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/overload_spec.rb;gitpull3 @@ -1,14 +1,36 @@ require File.dirname(__FILE__) + '/../../spec_helper' describe "Overload resolution" do + csc <<-EOL + public partial class ClassWithOverloads { + public string PublicProtectedOverload(){ + return "public overload"; + } + + protected string PublicProtectedOverload(string str) { + return "protected overload"; + } + } + EOL before(:each) do - @methods = ClassWithOverloads.new.method(:Overloaded) + @klass = ClassWithOverloads.new + @methods = @klass.method(:Overloaded) end it "is performed" do - @methods.call(100).to_s.should == "one arg" - @methods.call(100, 100).to_s.should == "two args" + @methods.call(100).should equal_clr_string("one arg") + @methods.call(100, 100).should equal_clr_string("two args") + @klass.overloaded(100).should equal_clr_string("one arg") + @klass.overloaded(100, 100).should equal_clr_string("two args") end + + it "correctly binds with methods of different visibility" do + method = @klass.method(:public_protected_overload) + @klass.public_protected_overload.should equal_clr_string("public overload") + @klass.public_protected_overload("abc").should equal_clr_string("protected overload") + method.call.should equal_clr_string("public overload") + method.call("abc").should equal_clr_string("protected overload") + end end describe "Selecting .NET overloads" do @@ -17,7 +39,7 @@ end it "is allowed" do - @methods.overloads(Fixnum,Fixnum).call(100,100).to_s.should == "two args" + @methods.overloads(Fixnum,Fixnum).call(100,100).should equal_clr_string("two args") end it "correctly reports error message" do =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/protected_spec.rb File: protected_spec.rb =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/protected_spec.rb;gitpull3 @@ -1,0 +1,47 @@ +require File.dirname(__FILE__) + '/../../spec_helper' + +describe "Invoking a protected .NET method" do + before :each do + @obj = ClassWithMethods.new + end + + it "works directly" do + @obj.protected_method.should equal_clr_string("protected") + end + + it "works via .send" do + @obj.send(:protected_method).should equal_clr_string("protected") + end + + it "works via .send" do + @obj.__send__(:protected_method).should equal_clr_string("protected") + end + + it "works via .instance_eval" do + @obj.instance_eval("protected_method").should equal_clr_string("protected") + end +end + +describe "Invoking a protected .NET method on an inherited Ruby class" do + class RubyClassWithMethods < ClassWithMethods + end + before :each do + @obj = RubyClassWithMethods.new + end + + it "works directly" do + @obj.protected_method.should equal_clr_string("protected") + end + + it "works via .send" do + @obj.send(:protected_method).should equal_clr_string("protected") + end + + it "works via .send" do + @obj.__send__(:protected_method).should equal_clr_string("protected") + end + + it "works via .instance_eval" do + @obj.instance_eval("protected_method").should equal_clr_string("protected") + end +end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/public_spec.rb;C791094 File: public_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/public_spec.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/invocation/public_spec.rb;gitpull3 @@ -6,18 +6,18 @@ end it "works directly" do - @obj.public_method.to_s.should == "public" + @obj.public_method.should equal_clr_string("public") end it "works via .send" do - @obj.send(:public_method).to_s.should == "public" + @obj.send(:public_method).should equal_clr_string("public") end it "works via .send" do - @obj.__send__(:public_method).to_s.should == "public" + @obj.__send__(:public_method).should equal_clr_string("public") end it "works via .instance_eval" do - @obj.instance_eval("public_method").to_s.should == "public" + @obj.instance_eval("public_method").should equal_clr_string("public") end end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/modification/override_spec.rb;C806904 File: override_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/modification/override_spec.rb;C806904 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/method/modification/override_spec.rb;gitpull3 @@ -14,18 +14,18 @@ it "is allowed via alias" do @obj.metaclass_temp_alias("_public_method","public_method") do - @obj._public_method.to_s.should == "public" + @obj._public_method.should equal_clr_string("public") end - @obj.public_method.to_s.should == "public" + @obj.public_method.should equal_clr_string("public") end it "is allowed via defining" do @obj.metaclass_temp_alias("_public_method", "public_method") do @obj.metaclass_def("public_method") {:not_public} @obj.public_method.should == :not_public - @obj._public_method.to_s.should == "public" + @obj._public_method.should equal_clr_string("public") end - @obj.public_method.to_s.should == "public" + @obj.public_method.should equal_clr_string("public") end it "maintains super method" do @@ -58,11 +58,11 @@ end it "call the correct method" do - @meth.bind(VirtualMethodOverrideNew.new).call.to_s.should == "virtual" + @meth.bind(VirtualMethodOverrideNew.new).call.should equal_clr_string("virtual") end it "call the correct method for overrides" do #override methods cannot be rebound - @meth.bind(VirtualMethodOverrideOverride.new).call.to_s.should == "override" + @meth.bind(VirtualMethodOverrideOverride.new).call.should equal_clr_string("override") end end =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/class add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/bcl/numerics add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/bcl/numerics/decimal_tags.txt File: decimal_tags.txt =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/bcl/numerics/decimal_tags.txt;gitpull3 @@ -1,0 +1,1 @@ +fails:C# decimal numbers should be able to check as equal to Float =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/class/instantiation add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/class/instantiation/class_tags.txt File: class_tags.txt =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/class/instantiation/class_tags.txt;gitpull3 @@ -1,0 +1,1 @@ +fails:Ruby classes derived from .NET classes with overloaded constructors properly selects overloaded constructors for super =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/invocation_tags.txt File: invocation_tags.txt =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/invocation_tags.txt;gitpull3 @@ -1,0 +1,4 @@ +fails:Invoking events works with methods via += +fails:Invoking events works with multiple objects via += +fails:Invoking events works with multiple of one callback via += +fails:Invoking events registers adds and removes =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/modification add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/modification/adding_tags.txt File: adding_tags.txt =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/modification/adding_tags.txt;gitpull3 @@ -1,0 +1,5 @@ +fails:Basic .NET events allow adding method handlers via += +fails:Basic .NET events allow adding lambda's via += +fails:Basic .NET events allow adding procs via += +fails:Basic .NET events allow adding multiple items via += +fails:Basic .NET events allow adding one item multiple times via += =================================================================== add: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/modification/removal_tags.txt File: removal_tags.txt =================================================================== --- [no source file] +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/tags/events/modification/removal_tags.txt;gitpull3 @@ -1,0 +1,6 @@ +fails:Basic .NET events allow removing method handlers via -= +fails:Basic .NET events allow removing lambda's via -= +fails:Basic .NET events allow removing procs via -= +fails:Basic .NET events allow removing multiple items via -= +fails:Basic .NET events allow removing one item multiple times via -= +fails:Basic .NET events allow removing one item more times than it is in the list via -= =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/typegroup/invocation/nongeneric_spec.rb;C791094 File: nongeneric_spec.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/typegroup/invocation/nongeneric_spec.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Interop/typegroup/invocation/nongeneric_spec.rb;gitpull3 @@ -15,4 +15,9 @@ lambda {StaticMethodTypeGroup.Return(100)}.should_not raise_error StaticMethodTypeGroup.Return(100).should == 100 end + + it "allow both generic and nongeneric members" do + lambda {System::Nullable}.should_not raise_error + lambda {System::Nullable.of(System::Int32)}.should_not raise_error + end end =================================================================== edit: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Scripts/csc.rb;C791094 File: csc.rb =================================================================== --- $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Scripts/csc.rb;C791094 (server) 4/3/2009 3:01 PM +++ Shelved Change: $/Dev10/feature/vs_langs01_s/Merlin/Main/Languages/Ruby/Tests/Scripts/csc.rb;gitpull3 @@ -32,7 +32,7 @@ puts header << ":" << string.to_s if $DEBUG end - def describe(string) + def describe(string, opts=nil) debug("describe", string) yield end @@ -46,9 +46,15 @@ def csc(code) debug("csc", code) - Compiler.code << "//" + caller[0] + file, line_number = caller[0].split(":") + Compiler.code << "#line #{line_number} \"#{file}\"" Compiler.code << code.strip end + + def reference(ref) + debug("reference", ref) + Compiler.refs << ref.strip + end end class Compiler @@ -74,6 +80,10 @@ @assemblies[@current].code end + def refs + @assemblies[@current].refs + end + def switch_to(name, options) unless @assemblies[name] @assemblies[name] = Assembly.new(@target_dir, options) @@ -88,19 +98,21 @@ end class Assembly - attr_accessor :code + attr_accessor :code, :refs def initialize(target_dir,options) @target_dir = target_dir @options = options @code = [] + @refs = [] end def compile(name) Dir.chdir(@target_dir) do + @code = @code.partition {|e| e.match /^\s*?using/}.flatten File.open(name, "w") {|f| f.write @code.join("\n")} opts = "" if @options[:references] - opts << " /r:#{@options[:references]}" + @refs << @options[:references] end if @options[:target] opts << " /t:#{@options[:target]}" @@ -108,7 +120,10 @@ if @options[:out] opts << " /out:#{@options[:out]}" end - cmd = "csc /t:library#{opts} #{name}" + @refs.each do |ref| + opts << " /r:#{ref}" + end + cmd = "csc /t:library /noconfig#{opts} #{name}" debug("compile", cmd) system cmd end ===================================================================