forked from tsai/mathnet-numerics
1066 changed files with 225390 additions and 0 deletions
@ -0,0 +1,57 @@ |
|||
Apache License, Version 2.0 |
|||
|
|||
Apache License |
|||
Version 2.0, January 2004 |
|||
http://www.apache.org/licenses/ |
|||
|
|||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION |
|||
|
|||
1. Definitions. |
|||
|
|||
"License" shall mean the terms and conditions for use, reproduction, and distribution as defined by Sections 1 through 9 of this document. |
|||
|
|||
"Licensor" shall mean the copyright owner or entity authorized by the copyright owner that is granting the License. |
|||
|
|||
"Legal Entity" shall mean the union of the acting entity and all other entities that control, are controlled by, or are under common control with that entity. For the purposes of this definition, "control" means (i) the power, direct or indirect, to cause the direction or management of such entity, whether by contract or otherwise, or (ii) ownership of fifty percent (50%) or more of the outstanding shares, or (iii) beneficial ownership of such entity. |
|||
|
|||
"You" (or "Your") shall mean an individual or Legal Entity exercising permissions granted by this License. |
|||
|
|||
"Source" form shall mean the preferred form for making modifications, including but not limited to software source code, documentation source, and configuration files. |
|||
|
|||
"Object" form shall mean any form resulting from mechanical transformation or translation of a Source form, including but not limited to compiled object code, generated documentation, and conversions to other media types. |
|||
|
|||
"Work" shall mean the work of authorship, whether in Source or Object form, made available under the License, as indicated by a copyright notice that is included in or attached to the work (an example is provided in the Appendix below). |
|||
|
|||
"Derivative Works" shall mean any work, whether in Source or Object form, that is based on (or derived from) the Work and for which the editorial revisions, annotations, elaborations, or other modifications represent, as a whole, an original work of authorship. For the purposes of this License, Derivative Works shall not include works that remain separable from, or merely link (or bind by name) to the interfaces of, the Work and Derivative Works thereof. |
|||
|
|||
"Contribution" shall mean any work of authorship, including the original version of the Work and any modifications or additions to that Work or Derivative Works thereof, that is intentionally submitted to Licensor for inclusion in the Work by the copyright owner or by an individual or Legal Entity authorized to submit on behalf of the copyright owner. For the purposes of this definition, "submitted" means any form of electronic, verbal, or written communication sent to the Licensor or its representatives, including but not limited to communication on electronic mailing lists, source code control systems, and issue tracking systems that are managed by, or on behalf of, the Licensor for the purpose of discussing and improving the Work, but excluding communication that is conspicuously marked or otherwise designated in writing by the copyright owner as "Not a Contribution." |
|||
|
|||
"Contributor" shall mean Licensor and any individual or Legal Entity on behalf of whom a Contribution has been received by Licensor and subsequently incorporated within the Work. |
|||
|
|||
2. Grant of Copyright License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable copyright license to reproduce, prepare Derivative Works of, publicly display, publicly perform, sublicense, and distribute the Work and such Derivative Works in Source or Object form. |
|||
|
|||
3. Grant of Patent License. Subject to the terms and conditions of this License, each Contributor hereby grants to You a perpetual, worldwide, non-exclusive, no-charge, royalty-free, irrevocable (except as stated in this section) patent license to make, have made, use, offer to sell, sell, import, and otherwise transfer the Work, where such license applies only to those patent claims licensable by such Contributor that are necessarily infringed by their Contribution(s) alone or by combination of their Contribution(s) with the Work to which such Contribution(s) was submitted. If You institute patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Work or a Contribution incorporated within the Work constitutes direct or contributory patent infringement, then any patent licenses granted to You under this License for that Work shall terminate as of the date such litigation is filed. |
|||
|
|||
4. Redistribution. You may reproduce and distribute copies of the Work or Derivative Works thereof in any medium, with or without modifications, and in Source or Object form, provided that You meet the following conditions: |
|||
|
|||
1. You must give any other recipients of the Work or Derivative Works a copy of this License; and |
|||
|
|||
2. You must cause any modified files to carry prominent notices stating that You changed the files; and |
|||
|
|||
3. You must retain, in the Source form of any Derivative Works that You distribute, all copyright, patent, trademark, and attribution notices from the Source form of the Work, excluding those notices that do not pertain to any part of the Derivative Works; and |
|||
|
|||
4. If the Work includes a "NOTICE" text file as part of its distribution, then any Derivative Works that You distribute must include a readable copy of the attribution notices contained within such NOTICE file, excluding those notices that do not pertain to any part of the Derivative Works, in at least one of the following places: within a NOTICE text file distributed as part of the Derivative Works; within the Source form or documentation, if provided along with the Derivative Works; or, within a display generated by the Derivative Works, if and wherever such third-party notices normally appear. The contents of the NOTICE file are for informational purposes only and do not modify the License. You may add Your own attribution notices within Derivative Works that You distribute, alongside or as an addendum to the NOTICE text from the Work, provided that such additional attribution notices cannot be construed as modifying the License. |
|||
|
|||
You may add Your own copyright statement to Your modifications and may provide additional or different license terms and conditions for use, reproduction, or distribution of Your modifications, or for any such Derivative Works as a whole, provided Your use, reproduction, and distribution of the Work otherwise complies with the conditions stated in this License. |
|||
|
|||
5. Submission of Contributions. Unless You explicitly state otherwise, any Contribution intentionally submitted for inclusion in the Work by You to the Licensor shall be under the terms and conditions of this License, without any additional terms or conditions. Notwithstanding the above, nothing herein shall supersede or modify the terms of any separate license agreement you may have executed with Licensor regarding such Contributions. |
|||
|
|||
6. Trademarks. This License does not grant permission to use the trade names, trademarks, service marks, or product names of the Licensor, except as required for reasonable and customary use in describing the origin of the Work and reproducing the content of the NOTICE file. |
|||
|
|||
7. Disclaimer of Warranty. Unless required by applicable law or agreed to in writing, Licensor provides the Work (and each Contributor provides its Contributions) on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied, including, without limitation, any warranties or conditions of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A PARTICULAR PURPOSE. You are solely responsible for determining the appropriateness of using or redistributing the Work and assume any risks associated with Your exercise of permissions under this License. |
|||
|
|||
8. Limitation of Liability. In no event and under no legal theory, whether in tort (including negligence), contract, or otherwise, unless required by applicable law (such as deliberate and grossly negligent acts) or agreed to in writing, shall any Contributor be liable to You for damages, including any direct, indirect, special, incidental, or consequential damages of any character arising as a result of this License or out of the use or inability to use the Work (including but not limited to damages for loss of goodwill, work stoppage, computer failure or malfunction, or any and all other commercial damages or losses), even if such Contributor has been advised of the possibility of such damages. |
|||
|
|||
9. Accepting Warranty or Additional Liability. While redistributing the Work or Derivative Works thereof, You may choose to offer, and charge a fee for, acceptance of support, warranty, indemnity, or other liability obligations and/or rights consistent with this License. However, in accepting such obligations, You may act only on Your own behalf and on Your sole responsibility, not on behalf of any other Contributor, and only if You agree to indemnify, defend, and hold each Contributor harmless for any liability incurred by, or claims asserted against, such Contributor by reason of your accepting any such warranty or additional liability. |
|||
|
|||
END OF TERMS AND CONDITIONS |
|||
@ -0,0 +1,37 @@ |
|||
<html> |
|||
<head> |
|||
<title>Cecil.FlowAnalysis.license</title> |
|||
<Style> |
|||
BODY, P, TD { font-family: Verdana, Arial, Helvetica, sans-serif; font-size: 10pt; color: #666666 } |
|||
H2,H3,H4,H5 { color: black; font-weight: bold; } |
|||
H2 { font-size: 13pt; } |
|||
H3 { font-size: 12pt; } |
|||
H4 { font-size: 10pt; color: black; } |
|||
</style> |
|||
</head> |
|||
<body bgcolor="#FFFFFF" color=#000000> |
|||
<p> |
|||
(C) 2005-2006 db4objects, Inc. http://www.db4o.com |
|||
</p> |
|||
<p> |
|||
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: |
|||
</p> |
|||
<p> |
|||
The above copyright notice and this permission notice shall be included in all copies |
|||
or substantial portions of the Software. |
|||
</p> |
|||
<p> |
|||
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. |
|||
</p> |
|||
</body> |
|||
</html> |
|||
@ -0,0 +1,83 @@ |
|||
<html> |
|||
<head><title>Credits</title></head> |
|||
<body> |
|||
<p> |
|||
Many people have donated their creativity, insight, time and effort |
|||
to the Gallio and MbUnit projects. |
|||
</p><p> |
|||
We would like to take a moment to recognize and thank these individuals. |
|||
</p> |
|||
<h3>Contributors</h3> |
|||
<p> |
|||
These people have contributed directly to this project as developers, |
|||
writers, editors, leaders, and promoters. |
|||
</p><p> |
|||
We thank them all for their careful attention to detail and work |
|||
in pursuit of excellence. |
|||
</p><p> |
|||
<ul> |
|||
<li><a href="http://der-albert.com">Albert Weinert</a>, developer</li> |
|||
<li><a href="http://weblogs.asp.net/astopford/">Andrew Stopford</a>, former lead of MbUnit</li> |
|||
<li><a href="http://Blog.BenHall.me.uk">Ben Hall</a>, developer and blogger</li> |
|||
<li><a href="http://www.hmobius.com">Dan Maharry</a>, documentation writer</li> |
|||
<li>Dave Griffiths, web developer</li> |
|||
<li>Eddy Young, developer</li> |
|||
<li>Francois Retief, developer</li> |
|||
<li>Graham Hay, developer</li> |
|||
<li><a href="http://blog.bits-in-motion.com">Jeff Brown</a>, lead of Gallio and MbUnit</li> |
|||
<li><a href="http://community.devpinoy.org/blogs/joeycalisay/">Joey Calisay</a>, developer</li> |
|||
<li>Johan Appelgren, developer</li> |
|||
<li><a href="http://blog.dotnetwiki.org/default.aspx">Jonathan "Peli" de Halleux</a>, creator of MbUnit</li> |
|||
<li><a href="http://techblog.julianhidalgo.com">Julian Hidalgo</a>, developer</li> |
|||
<li><a href="http://www.marcstober.com/blog/category/Software%20Blog">Marc Stober</a>, developer</a> |
|||
<li>Mark Haley, graphic artist and Gallio.org branding</li> |
|||
<li>Mike Sandberg, developer (AutoCAD integration)</li> |
|||
<li>Santosh Kumar Gottipamula, tester</li> |
|||
<li><a href="http://vadim-net.blogspot.com/">Vadim Kreynin</a>, developer</li> |
|||
<li><a href="http://www.interfacingreality.blogspot.com/">Yann Trévin</a>, developer and blogger</li> |
|||
</ul> |
|||
</p> |
|||
<h3>Acknowledgements</h3> |
|||
<p> |
|||
These people have contributed indirectly to this project as peers, |
|||
users, reviewers, bug reporters, friends and family. |
|||
</p><p> |
|||
We thank them all for their ideas, support and constructive criticism. |
|||
</p><p> |
|||
<ul> |
|||
<li>Brad Wilson, co-creator of xUnit.Net</li> |
|||
<li>Cathal Connolly, patches</li> |
|||
<li>Charlie Poole, lead of NUnit</li> |
|||
<li>Damir Gorenman, tester</li> |
|||
<li>Elizabeth Hanelt, spouse</li> |
|||
<li>Ilya Ryzhenkov, developer at JetBrains</li> |
|||
<li>James Newkirk, co-creator of xUnit.Net</li> |
|||
<li>Jamie Cansdale, creator of TestDriven.Net</li> |
|||
<li>Jay Flowers, creator of CI Factory</li> |
|||
<li>Jeroen van Menen, creator of WatiN</li> |
|||
<li>Joe O'Campo, co-creator of NBehave</li> |
|||
<li>Lior Friedman, developer at JetBrains</li> |
|||
<li>Manfred Lange, creator of CSUnit</li> |
|||
<li>Matthew Podwysocki, blogger</li> |
|||
<li>Oren "Ayende" Eini, blogger</li> |
|||
<li>Phil Haack, patches</li> |
|||
<li>Ray Johnson, employer</li> |
|||
<li>Roy Osherove, blogger</li> |
|||
<li>Todd Menier, patches</li> |
|||
<li>Tomas Chaloupka, patches</li> |
|||
</ul> |
|||
</p> |
|||
<h3>Final Thanks</h3> |
|||
<p> |
|||
In addition to these fine people, there are always countless others whose |
|||
efforts directly or indirectly supported this project. They produced |
|||
the tools we use, invented the ideas we borrowed, and offered a kind word |
|||
in a time of need. |
|||
</p><p> |
|||
We thank them all. |
|||
</p><p> |
|||
If you are one of these people and your name does not appear on this list, |
|||
please let us know and we shall update it. |
|||
</p> |
|||
</body> |
|||
</html> |
|||
@ -0,0 +1,14 @@ |
|||
Copyright 2005-2009 Gallio Project - http://www.gallio.org/ |
|||
Portions Copyright 2000-2004 Jonathan de Halleux |
|||
|
|||
Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0 |
|||
|
|||
Unless required by applicable law or agreed to in writing, software |
|||
distributed under the License is distributed on an "AS IS" BASIS, |
|||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
|||
See the License for the specific language governing permissions and |
|||
limitations under the License. |
|||
@ -0,0 +1,8 @@ |
|||
[InternetShortcut] |
|||
URL=http://www.gallio.org/ |
|||
IDList= |
|||
IconFile=http://www.mbunit.com/favicon.ico |
|||
IconIndex=1 |
|||
HotKey=0 |
|||
[{000214A0-0000-0000-C000-000000000046}] |
|||
Prop3=19,2 |
|||
@ -0,0 +1,8 @@ |
|||
[InternetShortcut] |
|||
URL=http://www.mbunit.com/ |
|||
IDList= |
|||
IconFile=http://www.mbunit.com/favicon.ico |
|||
IconIndex=1 |
|||
HotKey=0 |
|||
[{000214A0-0000-0000-C000-000000000046}] |
|||
Prop3=19,2 |
|||
@ -0,0 +1,36 @@ |
|||
<html> |
|||
<head> |
|||
<title>Mono.Cecil.license</title> |
|||
<Style> |
|||
BODY, P, TD { font-family: Verdana, Arial, Helvetica, sans-serif; font-size: 10pt; color: #666666 } |
|||
H2,H3,H4,H5 { color: black; font-weight: bold; } |
|||
H2 { font-size: 13pt; } |
|||
H3 { font-size: 12pt; } |
|||
H4 { font-size: 10pt; color: black; } |
|||
</style> |
|||
</head> |
|||
<body bgcolor="#FFFFFF" color=#000000> |
|||
<p> |
|||
(C) 2004-2006 Jb Evain |
|||
</p> |
|||
<p> |
|||
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: |
|||
</p> |
|||
<p> |
|||
The above copyright notice and this permission notice shall be included in all copies |
|||
or substantial portions of the Software. |
|||
</p> |
|||
<p> |
|||
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.</p> |
|||
</body> |
|||
</html> |
|||
@ -0,0 +1,38 @@ |
|||
<html> |
|||
<head> |
|||
<title>Mono.GetOptions.license</title> |
|||
<Style> |
|||
BODY, P, TD { font-family: Verdana, Arial, Helvetica, sans-serif; font-size: 10pt; color: #666666 } |
|||
H2,H3,H4,H5 { color: black; font-weight: bold; } |
|||
H2 { font-size: 13pt; } |
|||
H3 { font-size: 12pt; } |
|||
H4 { font-size: 10pt; color: black; } |
|||
</style> |
|||
</head> |
|||
<body bgcolor="#FFFFFF" color=#000000> |
|||
<p> |
|||
Mono.GetOptions - |
|||
(C) 2002, 2003, 2004, 2005 Rafael Teixeira |
|||
</p> |
|||
<p> |
|||
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: |
|||
</p> |
|||
<p> |
|||
The above copyright notice and this permission notice shall be included in all copies |
|||
or substantial portions of the Software. |
|||
</p> |
|||
<p> |
|||
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. |
|||
</p> |
|||
</body> |
|||
</html> |
|||
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,48 @@ |
|||
<?xml version="1.0" encoding="utf-8" ?> |
|||
<plugin pluginId="Gallio.AutoCAD.UI" |
|||
recommendedInstallationPath="AutoCAD" |
|||
xmlns="http://www.gallio.org/"> |
|||
<traits> |
|||
<name>AutoCAD Integration Plugin UI</name> |
|||
<version>3.1.0.0</version> |
|||
<description>AutoCAD plugin UI components.</description> |
|||
<icon>plugin://Gallio.AutoCAD/Resources/Gallio.AutoCAD.ico</icon> |
|||
</traits> |
|||
|
|||
<dependencies> |
|||
<dependency pluginId="Gallio" /> |
|||
<dependency pluginId="Gallio.UI" /> |
|||
<dependency pluginId="Gallio.AutoCAD" /> |
|||
</dependencies> |
|||
|
|||
<files> |
|||
<file path="Gallio.AutoCAD.UI.plugin" /> |
|||
<file path="Gallio.AutoCAD.UI.dll" /> |
|||
</files> |
|||
|
|||
<assemblies> |
|||
<assembly fullName="Gallio.AutoCAD.UI, Version=3.1.0.0, Culture=neutral, PublicKeyToken=eb9cfa67ee6ab36e" |
|||
codeBase="Gallio.AutoCAD.UI.dll" |
|||
qualifyPartialName="true" /> |
|||
</assemblies> |
|||
|
|||
<components> |
|||
<component componentId="Gallio.AutoCAD.UI.ControlPanel.RootPaneProvider" |
|||
serviceId="Gallio.UI.PreferencePaneProvider"> |
|||
<traits> |
|||
<path>AutoCAD</path> |
|||
<icon>plugin://Gallio.AutoCAD/Resources/Gallio.AutoCAD.ico</icon> |
|||
</traits> |
|||
</component> |
|||
|
|||
<component componentId="Gallio.AutoCAD.UI.ControlPanel.StartupPreferencePaneProvider" |
|||
serviceId="Gallio.UI.PreferencePaneProvider" |
|||
componentType="Gallio.AutoCAD.UI.ControlPanel.StartupPreferencePaneProvider, Gallio.AutoCAD.UI"> |
|||
<traits> |
|||
<path>AutoCAD/Startup</path> |
|||
<icon>plugin://Gallio.AutoCAD/Resources/Gallio.AutoCAD.ico</icon> |
|||
<scope>User</scope> |
|||
</traits> |
|||
</component> |
|||
</components> |
|||
</plugin> |
|||
Binary file not shown.
@ -0,0 +1,76 @@ |
|||
<?xml version="1.0" encoding="utf-8" ?> |
|||
<plugin pluginId="Gallio.AutoCAD" |
|||
recommendedInstallationPath="AutoCAD" |
|||
xmlns="http://www.gallio.org/"> |
|||
<traits> |
|||
<name>AutoCAD Integration Plugin</name> |
|||
<version>3.1.0.0</version> |
|||
<description>Provides support for testing ObjectARX extensions within AutoCAD.</description> |
|||
<icon>plugin://Gallio.AutoCAD/Resources/Gallio.AutoCAD.ico</icon> |
|||
</traits> |
|||
|
|||
<dependencies> |
|||
<dependency pluginId="Gallio" /> |
|||
</dependencies> |
|||
|
|||
<files> |
|||
<file path="Gallio.AutoCAD.plugin" /> |
|||
<file path="Gallio.AutoCAD.dll" /> |
|||
<file path="Gallio.AutoCAD.Plugin.dll" /> |
|||
<file path="objectarx_license.doc" /> |
|||
<file path="Resources\Gallio.AutoCAD.ico" /> |
|||
</files> |
|||
|
|||
<assemblies> |
|||
<assembly fullName="Gallio.AutoCAD, Version=3.1.0.0, Culture=neutral, PublicKeyToken=eb9cfa67ee6ab36e" |
|||
codeBase="Gallio.AutoCAD.dll" |
|||
qualifyPartialName="true" /> |
|||
</assemblies> |
|||
|
|||
<services> |
|||
<service serviceId="Gallio.AutoCAD.AcadLocator" |
|||
serviceType="Gallio.AutoCAD.IAcadLocator, Gallio.AutoCAD" /> |
|||
|
|||
<service serviceId="Gallio.AutoCAD.Preferences.AcadPreferenceManager" |
|||
serviceType="Gallio.AutoCAD.Preferences.IAcadPreferenceManager, Gallio.AutoCAD" /> |
|||
|
|||
<service serviceId="Gallio.AutoCAD.ProcessManagement.AcadProcessFactory" |
|||
serviceType="Gallio.AutoCAD.ProcessManagement.IAcadProcessFactory, Gallio.AutoCAD" /> |
|||
</services> |
|||
|
|||
<components> |
|||
<component componentId="Gallio.AutoCAD.AcadLocator" |
|||
serviceId="Gallio.AutoCAD.AcadLocator" |
|||
componentType="Gallio.AutoCAD.AcadLocator, Gallio.AutoCAD" /> |
|||
|
|||
<component componentId="Gallio.AutoCAD.Preferences.AcadPreferenceManager" |
|||
serviceId="Gallio.AutoCAD.Preferences.AcadPreferenceManager" |
|||
componentType="Gallio.AutoCAD.Preferences.AcadPreferenceManager, Gallio.AutoCAD" /> |
|||
|
|||
<component componentId="Gallio.AutoCAD.ProcessManagement.AcadProcessFactory" |
|||
serviceId="Gallio.AutoCAD.ProcessManagement.AcadProcessFactory" |
|||
componentType="Gallio.AutoCAD.ProcessManagement.AcadProcessFactory, Gallio.AutoCAD" /> |
|||
|
|||
<component componentId="AutoCAD.AcadTestRunnerFactory" |
|||
serviceId="Gallio.TestRunnerFactory" |
|||
componentType="Gallio.Runner.DefaultTestRunnerFactory, Gallio"> |
|||
<parameters> |
|||
<testIsolationProvider>${AutoCAD.AcadTestIsolationProvider}</testIsolationProvider> |
|||
</parameters> |
|||
<traits> |
|||
<name>AutoCAD</name> |
|||
<description> |
|||
Runs tests within an AutoCAD process. |
|||
|
|||
Supported test runner properties: |
|||
- AcadAttachToExisting: If "true" attaches to an existing AutoCAD process, otherwise starts a new one. |
|||
- AcadExePath: Specifies the full path of the "acad.exe" program. |
|||
</description> |
|||
</traits> |
|||
</component> |
|||
|
|||
<component componentId="AutoCAD.AcadTestIsolationProvider" |
|||
serviceId="Gallio.TestIsolationProvider" |
|||
componentType="Gallio.AutoCAD.Isolation.AcadTestIsolationProvider, Gallio.AutoCAD" /> |
|||
</components> |
|||
</plugin> |
|||
|
After Width: | Height: | Size: 287 KiB |
Binary file not shown.
Binary file not shown.
@ -0,0 +1,85 @@ |
|||
<?xml version="1.0" encoding="utf-8" ?> |
|||
<plugin pluginId="Gallio.CSUnitAdapter" |
|||
recommendedInstallationPath="CSUnit" |
|||
xmlns="http://www.gallio.org/"> |
|||
<traits> |
|||
<name>csUnit Adapter Plugin</name> |
|||
<version>3.1.0.0</version> |
|||
<description>Provides support for running csUnit tests.</description> |
|||
<icon>plugin://Gallio.CSUnitAdapter/Resources/csUnit.ico</icon> |
|||
</traits> |
|||
|
|||
<dependencies> |
|||
<dependency pluginId="Gallio" /> |
|||
</dependencies> |
|||
|
|||
<files> |
|||
<file path="Gallio.CSUnitAdapter.plugin" /> |
|||
<file path="Gallio.CSUnitAdapter.dll" /> |
|||
<file path="csUnit.dll" /> |
|||
<file path="csUnit.dll.tdnet" /> |
|||
<file path="csUnit.Common.dll" /> |
|||
<file path="csUnit.Interfaces.dll" /> |
|||
<file path="csUnit.Core.dll" /> |
|||
<file path="license.txt" /> |
|||
<file path="Readme.txt" /> |
|||
<file path="Resources\csUnit.ico" /> |
|||
</files> |
|||
|
|||
<assemblies> |
|||
<assembly fullName="Gallio.CSUnitAdapter, Version=3.1.0.0, Culture=neutral, PublicKeyToken=null" |
|||
codeBase="Gallio.CSUnitAdapter.dll" |
|||
qualifyPartialName="true"/> |
|||
|
|||
<assembly fullName="csUnit, Version=2.6.3374.34355, Culture=neutral, PublicKeyToken=6871f04765cca910" |
|||
codeBase="csUnit.dll"> |
|||
<bindingRedirects> |
|||
<bindingRedirect oldVersion="2.6.0.0-2.6.65535.65535" /> |
|||
</bindingRedirects> |
|||
</assembly> |
|||
|
|||
<assembly fullName="csUnit.Common, Version=2.6.3374.34355, Culture=neutral, PublicKeyToken=6871f04765cca910" |
|||
codeBase="csUnit.Common.dll"> |
|||
<bindingRedirects> |
|||
<bindingRedirect oldVersion="2.6.0.0-2.6.65535.65535" /> |
|||
</bindingRedirects> |
|||
</assembly> |
|||
|
|||
<assembly fullName="csUnit.Interfaces, Version=2.6.3374.34355, Culture=neutral, PublicKeyToken=6871f04765cca910" |
|||
codeBase="csUnit.Interfaces.dll"> |
|||
<bindingRedirects> |
|||
<bindingRedirect oldVersion="2.6.0.0-2.6.65535.65535" /> |
|||
</bindingRedirects> |
|||
</assembly> |
|||
|
|||
<assembly fullName="csUnit.Core, Version=2.6.3374.34355, Culture=neutral, PublicKeyToken=6871f04765cca910" |
|||
codeBase="csUnit.Core.dll"> |
|||
<bindingRedirects> |
|||
<bindingRedirect oldVersion="2.6.0.0-2.6.65535.65535" /> |
|||
</bindingRedirects> |
|||
</assembly> |
|||
</assemblies> |
|||
|
|||
<components> |
|||
<component componentId="CSUnitAdapter.TestFramework" |
|||
serviceId="Gallio.TestFramework" |
|||
componentType="Gallio.CSUnitAdapter.Model.CSUnitTestFramework, Gallio.CSUnitAdapter"> |
|||
<traits> |
|||
<name>csUnit</name> |
|||
<frameworkAssemblies>csUnit</frameworkAssemblies> |
|||
<version>2.6.3374.34355</version> |
|||
<fileTypes>Assembly</fileTypes> |
|||
<icon>plugin://Gallio.CSUnitAdapter/Resources/csUnit.ico</icon> |
|||
</traits> |
|||
</component> |
|||
|
|||
<component componentId="CSUnitAdapter.TestKinds.csUnitTestAssembly" |
|||
serviceId="Gallio.TestKind"> |
|||
<traits> |
|||
<name>csUnit Assembly</name> |
|||
<description>csUnit Test Assembly</description> |
|||
<icon>plugin://Gallio.CSUnitAdapter/Resources/csUnit.ico</icon> |
|||
</traits> |
|||
</component> |
|||
</components> |
|||
</plugin> |
|||
@ -0,0 +1,11 @@ |
|||
CSUnit Adapter Plugin |
|||
===================== |
|||
|
|||
This plugin uses the csUnit test runner to adapt csUnit tests so that |
|||
they can run within Gallio and be manipulated by Gallio-based tools. |
|||
|
|||
The plugin assembly is deliberately NOT signed using a strong name. |
|||
You can replace the underlying test framework with newer versions as |
|||
long as they are binary compatible with the originally distributed version. |
|||
|
|||
Home page: http://www.csunit.org/ |
|||
|
After Width: | Height: | Size: 1.1 KiB |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,6 @@ |
|||
<TestRunner> |
|||
<FriendlyName>csUnit v{0}.{1}.{2}</FriendlyName> |
|||
<AssemblyPath>..\TDNet\Gallio.TDNetRunner.dll</AssemblyPath> |
|||
<TypeName>Gallio.TDNetRunner.GallioResidentTestRunner</TypeName> |
|||
<TestRunnerType>Resident</TestRunnerType> |
|||
</TestRunner> |
|||
@ -0,0 +1,20 @@ |
|||
Copyright © 2002-2008 by Manfred Lange, Markus Renschler, Jake Anderson, |
|||
and Piers Lawson. All rights reserved. |
|||
|
|||
This software is provided 'as-is', without any express or implied warranty. In |
|||
no event will the authors be held liable for any damages arising from the use |
|||
of 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 following restrictions: |
|||
|
|||
1. The origin of this software must not be misrepresented; you must not claim |
|||
that you wrote the original software. If you use this software in a product, |
|||
an acknowledgment in the product documentation would be appreciated but is |
|||
not required. |
|||
|
|||
2. Altered source versions must be plainly marked as such, and must not be |
|||
misrepresented as being the original software. |
|||
|
|||
3. This notice may not be removed or altered from any source distribution. |
|||
Binary file not shown.
@ -0,0 +1,16 @@ |
|||
<?xml version='1.0' encoding='UTF-8'?> |
|||
<configuration> |
|||
<configSections> |
|||
<section name='microsoft.scripting' requirePermission='false' type='Microsoft.Scripting.Hosting.Configuration.Section, Microsoft.Scripting, Version=0.9.6.10, Culture=neutral, PublicKeyToken=31bf3856ad364e35'/> |
|||
</configSections> |
|||
|
|||
<microsoft.scripting> |
|||
<languages> |
|||
<language extensions='.rb' displayName='IronRuby' type='IronRuby.Runtime.RubyContext, IronRuby, Version=0.6.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35' names='IronRuby;Ruby;rb'/> |
|||
</languages> |
|||
|
|||
<options> |
|||
<set language='IronRuby' option='LibraryPaths' value='Scripts\IronRuby;libs\IronRuby\lib\IronRuby;libs\IronRuby\lib\ruby\site_ruby\1.8;libs\IronRuby\lib\ruby\site_ruby;libs\IronRuby\lib\ruby\1.8;..\libs\IronRuby\lib\IronRuby;..\libs\IronRuby\lib\ruby\site_ruby\1.8;..\libs\IronRuby\lib\ruby\site_ruby;..\libs\IronRuby\lib\ruby\1.8'/> |
|||
</options> |
|||
</microsoft.scripting> |
|||
</configuration> |
|||
@ -0,0 +1,645 @@ |
|||
<?xml version="1.0" encoding="utf-8" ?> |
|||
<plugin pluginId="Gallio.DLRIntegration" |
|||
recommendedInstallationPath="DLR" |
|||
xmlns="http://www.gallio.org/"> |
|||
<traits> |
|||
<name>Dynamic Language Runtime Integration Plugin</name> |
|||
<version>3.1.0.0</version> |
|||
<description>Integrates the Dynamic Language Runtime with Gallio.</description> |
|||
</traits> |
|||
|
|||
<dependencies> |
|||
<dependency pluginId="Gallio" /> |
|||
</dependencies> |
|||
|
|||
<probingPaths> |
|||
<probingPath>libs</probingPath> |
|||
<probingPath>..\libs</probingPath> |
|||
</probingPaths> |
|||
|
|||
<files> |
|||
<file path="Gallio.DLRIntegration.plugin" /> |
|||
<file path="Gallio.DLRIntegration.dll" /> |
|||
<!-- The following tokens are replaced during the build. --> |
|||
<file path="libs\ir.exe"/> |
|||
<file path="libs\ir.exe.config"/> |
|||
<file path="libs\IronRuby.dll"/> |
|||
<file path="libs\IronRuby.Libraries.dll"/> |
|||
<file path="libs\IronRuby.Libraries.Yaml.dll"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\bigdecimal.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\digest.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\digest\md5.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\digest\sha1.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\enumerator.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\etc.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\fcntl.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\hacks.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\iconv.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\IronRuby.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\nkf.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\openssl.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\parse_tree.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\PresentationCore.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\PresentationFramework.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\prime.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\rbconfig.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\socket.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\stringio.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\strscan.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\syslog.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\System.Data.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\System.Drawing.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\system.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\System.Windows.Forms.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\test\unit.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\test\unit\autorunner.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\test\unit\testcase.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\thread.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\tmpdir.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\WindowsBase.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\yaml.rb"/> |
|||
<file path="libs\IronRuby\lib\IronRuby\zlib.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\abbrev.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\base64.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\benchmark.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\bigdecimal\jacobian.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\bigdecimal\ludcmp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\bigdecimal\math.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\bigdecimal\newton.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\bigdecimal\util.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\cgi-lib.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\cgi.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\cgi\session.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\cgi\session\pstore.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\complex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\csv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\date.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\date2.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\date\format.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\debug.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\delegate.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\digest.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\digest\sha2.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\dl\import.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\dl\struct.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\dl\types.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\dl\win32.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\acl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\drb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\eq.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\extserv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\extservm.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\gw.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\invokemethod.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\observer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\ssl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\timeridconv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\drb\unix.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\e2mmap.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\English.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\Env.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\erb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\eregex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\fileutils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\finalize.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\find.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\forwardable.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\ftools.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\getoptlong.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\getopts.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\gserver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\importenv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\io\nonblock.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\ipaddr.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\chws.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\fork.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\help.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\load.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\nop.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\pushws.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\cmd\subirb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\completion.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\context.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\extend-command.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\change-ws.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\history.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\loader.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\math-mode.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\multi-irb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\save-history.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\tracer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\use-loader.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ext\workspaces.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\frame.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\help.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\init.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\input-method.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\lc\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\lc\help-message"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\lc\ja\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\lc\ja\help-message"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\locale.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\notifier.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\output-method.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ruby-lex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ruby-token.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\slex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\version.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\workspace.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\ws-for-case-2.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\irb\xmp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\jcode.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\kconv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\logger.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\mailread.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\mathn.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\matrix.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\md5.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\mkmf.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\monitor.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\mutex_m.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\ftp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\ftptls.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\http.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\https.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\imap.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\pop.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\protocol.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\smtp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\telnet.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\net\telnets.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\observer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\open-uri.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\open3.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\bn.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\buffering.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\cipher.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\digest.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\ssl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\openssl\x509.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse\date.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse\shellwords.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse\time.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse\uri.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\optparse\version.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\ostruct.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\parsearg.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\parsedate.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\pathname.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\ping.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\pp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\prettyprint.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\profile.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\profiler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\pstore.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\racc\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rational.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rbconfig.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\code_objects.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\diagram.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\dot\dot.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\chm_generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\html_generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\ri_generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\chm\chm.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\html\hefss.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\html\html.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\html\kilmer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\html\old_html.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\html\one_page_html.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\xml\rdf.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\template\xml\xml.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\generators\xml_generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\sample\rdoc2latex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\sample\sample.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\fragments.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\inline.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\lines.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\preprocess.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\to_flow.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\to_html.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\simple_markup\to_latex.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\test\AllTests.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\test\TestInline.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\markup\test\TestParse.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\options.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\parsers\parserfactory.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\parsers\parse_c.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\parsers\parse_f95.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\parsers\parse_rb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\parsers\parse_simple.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\rdoc.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_cache.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_descriptions.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_display.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_driver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_formatter.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_options.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_paths.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_reader.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_util.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\ri\ri_writer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\template.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\tokenstream.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rdoc\usage.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\readbytes.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\resolv-replace.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\resolv.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\attlistdecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\attribute.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\cdata.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\child.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\comment.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\doctype.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\document.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\dtd\attlistdecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\dtd\dtd.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\dtd\elementdecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\dtd\entitydecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\dtd\notationdecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\element.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encoding.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\CP-1252.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\EUC-JP.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\ICONV.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\ISO-8859-1.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\ISO-8859-15.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\SHIFT-JIS.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\SHIFT_JIS.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\UNILE.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\US-ASCII.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\UTF-16.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\encodings\UTF-8.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\entity.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\formatters\default.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\formatters\pretty.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\formatters\transitive.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\functions.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\instruction.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\light\node.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\namespace.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\node.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\output.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parent.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parseexception.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\baseparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\lightparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\pullparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\sax2parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\streamparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\treeparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\ultralightparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\parsers\xpathparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\quickpath.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\rexml.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\sax2listener.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\source.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\streamlistener.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\syncenumerator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\text.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\undefinednamespaceexception.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\validation\relaxng.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\validation\validation.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\validation\validationexception.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\xmldecl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\xmltokens.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\xpath.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rexml\xpath_parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rinda\rinda.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rinda\ring.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rinda\tuplespace.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\0.9.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\1.0.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\2.0.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\content.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\converter.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\dublincore.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\image.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\0.9.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\1.0.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\2.0.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\base.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\content.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\dublincore.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\image.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\syndication.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\taxonomy.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\maker\trackback.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\rexmlparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\rss.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\syndication.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\taxonomy.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\trackback.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\utils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\xml-stylesheet.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\xmlparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rss\xmlscanner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\rubyunit.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\assert.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\cui\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\testcase.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\testresult.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\testsuite.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\runit\topublic.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\scanf.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\set.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\sha1.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shellwords.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\builtin-command.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\command-processor.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\filter.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\process-controller.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\system-command.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\shell\version.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\singleton.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\attachment.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\baseData.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\element.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\encodingstyle\aspDotNetHandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\encodingstyle\handler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\encodingstyle\literalHandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\encodingstyle\soapHandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\generator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\header\handler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\header\handlerset.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\header\simplehandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\httpconfigloader.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\factory.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\mapping.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\registry.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\rubytypeFactory.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\typeMap.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\wsdlencodedregistry.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mapping\wsdlliteralregistry.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\marshal.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\mimemessage.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\netHttpClient.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\processor.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\property.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\cgistub.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\driver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\element.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\httpserver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\proxy.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\router.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\rpc.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\soaplet.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\rpc\standaloneServer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\soap.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\streamHandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\soap\wsdlDriver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\sync.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\tempfile.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\assertionfailederror.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\assertions.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\autorunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\collector.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\collector\dir.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\collector\objectspace.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\failure.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\testcase.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\testresult.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\testsuite.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\console\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\fox\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\gtk2\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\gtk\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\testrunnermediator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\testrunnerutilities.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\ui\tk\testrunner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\util\backtracefilter.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\util\observable.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\test\unit\util\procwrapper.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\thread.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\thwait.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\time.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\timeout.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\tmpdir.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\tracer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\tsort.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\un.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\common.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\ftp.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\generic.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\http.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\https.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\ldap.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\uri\mailto.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\weakref.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\accesslog.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\cgi.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\compat.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\config.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\cookie.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\htmlutils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\authenticator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\basicauth.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\digestauth.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\htdigest.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\htgroup.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\htpasswd.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpauth\userdb.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpproxy.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httprequest.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpresponse.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\https.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpserver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\abstract.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\cgihandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\cgi_runner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\erbhandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\filehandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpservlet\prochandler.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpstatus.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httputils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\httpversion.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\log.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\server.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\ssl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\utils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\webrick\version.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\binding.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\data.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\definitions.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\documentation.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\import.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\importer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\info.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\message.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\operation.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\operationBinding.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\param.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\part.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\port.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\portType.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\service.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\address.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\binding.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\body.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\cgiStubCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\classDefCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\classDefCreatorSupport.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\clientSkeltonCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\complexType.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\data.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\definitions.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\driverCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\element.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\fault.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\header.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\headerfault.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\mappingRegistryCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\methodDefCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\operation.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\servantSkeltonCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\standaloneServerStubCreator.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\soap\wsdl2ruby.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\types.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\wsdl.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\all.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\annotation.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\any.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\attribute.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\choice.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\complexContent.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\complexType.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\content.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\data.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\element.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\enumeration.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\import.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\importer.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\include.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\length.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\pattern.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\schema.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\sequence.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\simpleContent.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\simpleExtension.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\simpleRestriction.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\simpleType.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\unique.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\wsdl\xmlSchema\xsd2ruby.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\base64.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\client.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\config.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\create.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\datetime.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\httpserver.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\marshal.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\server.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xmlrpc\utils.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\charset.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen\classdef.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen\commentdef.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen\gensupport.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen\methoddef.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\codegen\moduledef.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\datatypes.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\datatypes1999.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\iconvcharset.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\mapping.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\namedelements.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\ns.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\qname.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\xmlparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\xmlparser\parser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\xmlparser\rexmlparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\xmlparser\xmlparser.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\xsd\xmlparser\xmlscanner.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\baseemitter.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\basenode.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\constants.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\dbm.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\encoding.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\error.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\loader.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\rubytypes.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\store.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\stream.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\stringio.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\syck.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\tag.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\types.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\yamlnode.rb"/> |
|||
<file path="libs\IronRuby\lib\ruby\1.8\yaml\ypath.rb"/> |
|||
<file path="libs\LICENSE.CPL.txt"/> |
|||
<file path="libs\LICENSE.MSPL.html"/> |
|||
<file path="libs\LICENSE.Ruby.txt"/> |
|||
<file path="libs\Microsoft.Dynamic.dll"/> |
|||
<file path="libs\Microsoft.Scripting.Core.dll"/> |
|||
<file path="libs\Microsoft.Scripting.dll"/> |
|||
<file path="libs\Microsoft.Scripting.ExtensionAttribute.dll"/> |
|||
<file path="scripts\IronRuby\gallio.rb"/> |
|||
<file path="scripts\IronRuby\gallio\wrappers.rb"/> |
|||
<file path="scripts\IronRuby\gallio\wrappers\logger.rb"/> |
|||
<file path="scripts\IronRuby\gallio\wrappers\message_sink.rb"/> |
|||
<file path="scripts\IronRuby\gallio\wrappers\progress_monitor.rb"/> |
|||
<file path="scripts\IronRuby\gallio\wrappers\runtime.rb"/> |
|||
</files> |
|||
|
|||
<assemblies> |
|||
<assembly fullName="Gallio.DLRIntegration, Version=3.1.0.0, Culture=neutral, PublicKeyToken=null" |
|||
codeBase="Gallio.DLRIntegration.dll" |
|||
qualifyPartialName="true" /> |
|||
|
|||
<assembly fullName="Microsoft.Dynamic, Version=0.9.6.10, Culture=neutral, PublicKeyToken=31bf3856ad364e35" |
|||
codeBase="Microsoft.Dynamic.dll" /> |
|||
|
|||
<assembly fullName="Microsoft.Scripting, Version=0.9.6.10, Culture=neutral, PublicKeyToken=31bf3856ad364e35" |
|||
codeBase="Microsoft.Scripting.dll" /> |
|||
|
|||
<assembly fullName="Microsoft.Scripting.Core, Version=0.9.6.10, Culture=neutral, PublicKeyToken=31bf3856ad364e35" |
|||
codeBase="Microsoft.Scripting.Core.dll" /> |
|||
|
|||
<assembly fullName="Microsoft.Scripting.ExtensionAttribute, Version=2.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" |
|||
codeBase="Microsoft.Scripting.ExtensionAttribute.dll" /> |
|||
</assemblies> |
|||
|
|||
<components> |
|||
<!-- DLR File types --> |
|||
|
|||
<component componentId="DLRIntegration.FileTypeRecognizers.RubySource" |
|||
serviceId="Gallio.FileTypeRecognizer"> |
|||
<traits> |
|||
<id>RubySource</id> |
|||
<description>A Ruby source file.</description> |
|||
<fileNameRegex>.*\.rb</fileNameRegex> |
|||
</traits> |
|||
</component> |
|||
|
|||
<component componentId="DLRIntegration.FileTypeRecognizers.PythonSource" |
|||
serviceId="Gallio.FileTypeRecognizer"> |
|||
<traits> |
|||
<id>PythonSource</id> |
|||
<description>A Python source file.</description> |
|||
<fileNameRegex>.*\.py</fileNameRegex> |
|||
</traits> |
|||
</component> |
|||
</components> |
|||
</plugin> |
|||
@ -0,0 +1,7 @@ |
|||
# |
|||
# Gallio integration classes for IronRuby. |
|||
# |
|||
|
|||
load_assembly 'Gallio' |
|||
|
|||
require 'gallio/wrappers' |
|||
@ -0,0 +1,8 @@ |
|||
# |
|||
# Provides wrappers for Gallio types and services. |
|||
# |
|||
|
|||
require 'gallio/wrappers/logger.rb' |
|||
require 'gallio/wrappers/message_sink.rb' |
|||
require 'gallio/wrappers/progress_monitor.rb' |
|||
require 'gallio/wrappers/runtime.rb' |
|||
@ -0,0 +1,41 @@ |
|||
# |
|||
# A wrapper for ILogger. |
|||
# |
|||
|
|||
module Gallio |
|||
module Wrappers |
|||
class Logger |
|||
attr_reader :inner |
|||
|
|||
def initialize(inner) |
|||
@inner = inner |
|||
end |
|||
|
|||
def error(message) |
|||
log(::Gallio::Runtime::Logging::LogSeverity.Error, message) |
|||
end |
|||
|
|||
def warning(message) |
|||
log(::Gallio::Runtime::Logging::LogSeverity.Warning, message) |
|||
end |
|||
|
|||
def important(message) |
|||
log(::Gallio::Runtime::Logging::LogSeverity.Important, message) |
|||
end |
|||
|
|||
def info(message) |
|||
log(::Gallio::Runtime::Logging::LogSeverity.Info, message) |
|||
end |
|||
|
|||
def debug(message) |
|||
log(::Gallio::Runtime::Logging::LogSeverity.Debug, message) |
|||
end |
|||
|
|||
private |
|||
|
|||
def log(severity, message) |
|||
@inner.Log(severity, message) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,19 @@ |
|||
# |
|||
# A wrapper for IMessageSink |
|||
# |
|||
|
|||
module Gallio |
|||
module Wrappers |
|||
class MessageSink |
|||
attr_reader :inner |
|||
|
|||
def initialize(inner) |
|||
@inner = inner |
|||
end |
|||
|
|||
def publish(message) |
|||
@inner.Publish(message) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,39 @@ |
|||
# |
|||
# A wrapper for IProgressMonitor |
|||
# |
|||
|
|||
module Gallio |
|||
module Wrappers |
|||
class ProgressMonitor |
|||
attr_reader :inner |
|||
|
|||
def initialize(inner) |
|||
@inner = inner |
|||
end |
|||
|
|||
def begin_task(task_name, total_work_units) |
|||
@inner.BeginTask(task_name, total_work_units) |
|||
end |
|||
|
|||
def done() |
|||
@inner.Done() |
|||
end |
|||
|
|||
def is_canceled? |
|||
@inner.IsCanceled |
|||
end |
|||
|
|||
def set_status(message) |
|||
@inner.SetStatus(message) |
|||
end |
|||
|
|||
def worked(work_units) |
|||
@inner.Worked(work_units) |
|||
end |
|||
|
|||
def create_sub_progress_monitor(parent_work_units) |
|||
new(@inner.CreateSubProgressMonitor(parent_work_units)) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,13 @@ |
|||
# |
|||
# A wrapper for the runtime. |
|||
# |
|||
|
|||
module Gallio |
|||
module Wrappers |
|||
class Runtime |
|||
def self.Resolve(service_type_module) |
|||
::Gallio::Runtime::RuntimeAccessor.ServiceLocator.Resolve(service_type_module.to_clr_type) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
Binary file not shown.
Binary file not shown.
Binary file not shown.
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
warn("IronRuby library is built-in and doesn't need to be required anymore") |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'PresentationCore, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'PresentationFramework, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'System.Data, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'System.Drawing, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require "System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require "WindowsBase, Version=3.0.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35" |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.BigDecimal' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Digest' |
|||
@ -0,0 +1,17 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'digest' |
|||
# placeholder no-op file |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'digest' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Enumerator' |
|||
@ -0,0 +1,17 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
|
|||
# No-op file since we won't support this under Windows |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.FileControl' |
|||
@ -0,0 +1,55 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
# In non-iirb sessions, TOPLEVEL_BINDING isn't defined |
|||
unless defined?(TOPLEVEL_BINDING) |
|||
TOPLEVEL_BINDING = binding |
|||
end |
|||
|
|||
# IronRuby bug: IO#read seems to chop off the first char |
|||
|
|||
class TCPSocket |
|||
def read size |
|||
recv size |
|||
end |
|||
end |
|||
|
|||
# Subclass Tracking |
|||
|
|||
module SubclassTracking |
|||
class Holder < Array |
|||
def each_object(klass, &b) |
|||
self.each { |c| b[c] } |
|||
end |
|||
end |
|||
def self.extended(klass) |
|||
(class << klass; self; end).send :attr_accessor, :subclasses |
|||
(class << klass; self; end).send :define_method, :inherited do |klazz| |
|||
klass.subclasses << klazz |
|||
super |
|||
end |
|||
klass.subclasses = Holder.new |
|||
end |
|||
end |
|||
|
|||
class IO |
|||
def flush; end # nop |
|||
end |
|||
|
|||
class String |
|||
def hex |
|||
self.to_i(16) |
|||
end |
|||
end |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Iconv' |
|||
@ -0,0 +1,33 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
# HACKHACKHACK: Stub implementation of NKF |
|||
|
|||
module NKF |
|||
AUTO = 0 |
|||
JIS = 1 |
|||
EUC = 2 |
|||
SJIS = 3 |
|||
NOCONV = 4 |
|||
ASCII = 5 |
|||
BINARY = 4 |
|||
NKF_RELEASE_DATE = "2007-01-28" |
|||
NKF_VERSION = "2.0.8" |
|||
UNKNOWN = 0 |
|||
UTF16 = 8 |
|||
UTF32 = 12 |
|||
UTF8 = 6 |
|||
VERSION = "2.0.8 (2007-01-28)" |
|||
end |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.OpenSsl' |
|||
@ -0,0 +1,253 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
abort "*** Sorry, ParseTree doesn't work with ruby #{RUBY_VERSION}" if |
|||
RUBY_VERSION >= "1.9" |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.ParseTree' |
|||
|
|||
class Module |
|||
def modules |
|||
ancestors[1..-1] |
|||
end |
|||
end |
|||
|
|||
class Class |
|||
def modules |
|||
a = self.ancestors |
|||
a[1..a.index(superclass)-1] |
|||
end |
|||
end |
|||
|
|||
## |
|||
# ParseTree is a RubyInline-style extension that accesses and |
|||
# traverses the internal parse tree created by ruby. |
|||
# |
|||
# class Example |
|||
# def blah |
|||
# return 1 + 1 |
|||
# end |
|||
# end |
|||
# |
|||
# ParseTree.new.parse_tree(Example) |
|||
# => [[:class, :Example, :Object, |
|||
# [:defn, |
|||
# "blah", |
|||
# [:scope, |
|||
# [:block, |
|||
# [:args], |
|||
# [:return, [:call, [:lit, 1], "+", [:array, [:lit, 1]]]]]]]]] |
|||
|
|||
class ParseTree |
|||
|
|||
VERSION = '2.1.1' |
|||
|
|||
## |
|||
# Front end translation method. |
|||
|
|||
def self.translate(klass_or_str, method=nil) |
|||
pt = self.new(false) |
|||
case klass_or_str |
|||
when String then |
|||
sexp = pt.parse_tree_for_string(klass_or_str).first |
|||
if method then |
|||
# class, scope, block, *methods |
|||
sexp.last.last[1..-1].find do |defn| |
|||
defn[1] == method |
|||
end |
|||
else |
|||
sexp |
|||
end |
|||
else |
|||
unless method.nil? then |
|||
if method.to_s =~ /^self\./ then |
|||
method = method.to_s[5..-1].intern |
|||
pt.parse_tree_for_method(klass_or_str, method, true) |
|||
else |
|||
pt.parse_tree_for_method(klass_or_str, method) |
|||
end |
|||
else |
|||
pt.parse_tree(klass_or_str).first |
|||
end |
|||
end |
|||
end |
|||
|
|||
## |
|||
# Initializes a ParseTree instance. Includes newline nodes if |
|||
# +include_newlines+ which defaults to +$DEBUG+. |
|||
|
|||
def initialize(include_newlines=$DEBUG) |
|||
@include_newlines = include_newlines |
|||
end |
|||
|
|||
## |
|||
# Main driver for ParseTree. Returns an array of arrays containing |
|||
# the parse tree for +klasses+. |
|||
# |
|||
# Structure: |
|||
# |
|||
# [[:class, classname, superclassname, [:defn :method1, ...], ...], ...] |
|||
# |
|||
# NOTE: v1.0 - v1.1 had the signature (klass, meth=nil). This wasn't |
|||
# used much at all and since parse_tree_for_method already existed, |
|||
# it was deemed more useful to expand this method to do multiple |
|||
# classes. |
|||
|
|||
def parse_tree(*klasses) |
|||
result = [] |
|||
klasses.each do |klass| |
|||
klassname = klass.name rescue '' # HACK klass.name should never be nil |
|||
# Tempfile's DelegateClass(File) seems to |
|||
# cause this |
|||
klassname = "UnnamedClass_#{klass.object_id}" if klassname.empty? |
|||
klassname = klassname.to_sym |
|||
|
|||
code = if Class === klass then |
|||
sc = klass.superclass |
|||
sc_name = ((sc.nil? or sc.name.empty?) ? "nil" : sc.name).intern |
|||
[:class, klassname, [:const, sc_name]] |
|||
else |
|||
[:module, klassname] |
|||
end |
|||
|
|||
method_names = [] |
|||
method_names += klass.instance_methods false |
|||
method_names += klass.private_instance_methods false |
|||
# protected methods are included in instance_methods, go figure! |
|||
|
|||
method_names.sort.each do |m| |
|||
r = parse_tree_for_method(klass, m.to_sym) |
|||
code << r |
|||
end |
|||
|
|||
klass.modules.each do |mod| # TODO: add a test for this |
|||
mod.instance_methods.each do |m| |
|||
r = parse_tree_for_method(mod, m.to_sym) |
|||
code << r |
|||
end |
|||
end |
|||
|
|||
klass.singleton_methods(false).sort.each do |m| |
|||
code << parse_tree_for_method(klass, m.to_sym, true) |
|||
end |
|||
|
|||
result << code |
|||
end |
|||
return result |
|||
end |
|||
|
|||
## |
|||
# Returns the parse tree for just one +method+ of a class +klass+. |
|||
# |
|||
# Format: |
|||
# |
|||
# [:defn, :name, :body] |
|||
|
|||
def parse_tree_for_method(klass, method, is_cls_meth=false) |
|||
$stderr.puts "** parse_tree_for_method(#{klass}, #{method}):" if $DEBUG |
|||
r = parse_tree_for_meth(klass, method.to_sym, is_cls_meth) |
|||
r |
|||
end |
|||
|
|||
## |
|||
# Returns the parse tree for a string +source+. |
|||
# |
|||
# Format: |
|||
# |
|||
# [[sexps] ... ] |
|||
|
|||
def parse_tree_for_string(source, filename = '(string)', line = 1) |
|||
old_verbose, $VERBOSE = $VERBOSE, true |
|||
return parse_tree_for_str0(source, filename, line) |
|||
ensure |
|||
$VERBOSE = old_verbose |
|||
end |
|||
|
|||
def parse_tree_for_str0(*__1args2__) # :nodoc: |
|||
parse_tree_for_str(*__1args2__) # just helps clean up the binding |
|||
end |
|||
|
|||
if RUBY_VERSION < "1.8.4" then |
|||
inline do |builder| |
|||
builder.add_type_converter("bool", '', '') |
|||
builder.c_singleton " |
|||
bool has_alloca() { |
|||
(void)self; |
|||
#ifdef C_ALLOCA |
|||
return Qtrue; |
|||
#else |
|||
return Qfalse; |
|||
#endif |
|||
}" |
|||
end |
|||
else |
|||
def self.has_alloca |
|||
true |
|||
end |
|||
end |
|||
|
|||
|
|||
NODE_NAMES = [ |
|||
# 00 |
|||
:method, :fbody, :cfunc, :scope, :block, |
|||
:if, :case, :when, :opt_n, :while, |
|||
# 10 |
|||
:until, :iter, :for, :break, :next, |
|||
:redo, :retry, :begin, :rescue, :resbody, |
|||
# 20 |
|||
:ensure, :and, :or, :not, :masgn, |
|||
:lasgn, :dasgn, :dasgn_curr, :gasgn, :iasgn, |
|||
# 30 |
|||
:cdecl, :cvasgn, :cvdecl, :op_asgn1, :op_asgn2, |
|||
:op_asgn_and, :op_asgn_or, :call, :fcall, :vcall, |
|||
# 40 |
|||
:super, :zsuper, :array, :zarray, :hash, |
|||
:return, :yield, :lvar, :dvar, :gvar, |
|||
# 50 |
|||
:ivar, :const, :cvar, :nth_ref, :back_ref, |
|||
:match, :match2, :match3, :lit, :str, |
|||
# 60 |
|||
:dstr, :xstr, :dxstr, :evstr, :dregx, |
|||
:dregx_once, :args, :argscat, :argspush, :splat, |
|||
# 70 |
|||
:to_ary, :svalue, :block_arg, :block_pass, :defn, |
|||
:defs, :alias, :valias, :undef, :class, |
|||
# 80 |
|||
:module, :sclass, :colon2, :colon3, :cref, |
|||
:dot2, :dot3, :flip2, :flip3, :attrset, |
|||
# 90 |
|||
:self, :nil, :true, :false, :defined, |
|||
# 95 |
|||
:newline, :postexe, :alloca, :dmethod, :bmethod, |
|||
# 100 |
|||
:memo, :ifunc, :dsym, :attrasgn, |
|||
:last |
|||
] |
|||
|
|||
if RUBY_VERSION > "1.9" then |
|||
NODE_NAMES.insert NODE_NAMES.index(:hash), :values |
|||
NODE_NAMES.insert NODE_NAMES.index(:defined), :errinfo |
|||
NODE_NAMES.insert NODE_NAMES.index(:last), :prelude, :lambda |
|||
NODE_NAMES.delete :dmethod |
|||
NODE_NAMES[128] = NODE_NAMES.delete :newline |
|||
end |
|||
|
|||
############################################################ |
|||
# END of rdoc methods |
|||
############################################################ |
|||
|
|||
include ::IronRuby::ParseTree |
|||
|
|||
end # ParseTree class |
|||
@ -0,0 +1,21 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
#placeholder for either throwing an error, or implementing a readline library |
|||
#the basics here are just to past specs |
|||
class Prime |
|||
def self.instance |
|||
end |
|||
end |
|||
@ -0,0 +1,177 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
|
|||
module Config |
|||
RUBY_VERSION == "1.8.6" or |
|||
raise "ruby lib version (1.8.6) doesn't match executable version (#{RUBY_VERSION})" |
|||
|
|||
CONFIG = {} |
|||
CONFIG["MAJOR"] = "1" |
|||
CONFIG["MINOR"] = "8" |
|||
CONFIG["TEENY"] = "6" |
|||
CONFIG["PATCHLEVEL"] = "0" |
|||
CONFIG["EXEEXT"] = ".exe" |
|||
# This value is used by libraries to spawn new processes to run Ruby scripts. Hence it needs to match the ir.exe name |
|||
CONFIG["ruby_install_name"] = "ir" |
|||
CONFIG["RUBY_INSTALL_NAME"] = "ir" |
|||
CONFIG["RUBY_SO_NAME"] = "msvcrt-ruby18" |
|||
CONFIG["SHELL"] = "$(COMSPEC)" |
|||
CONFIG["BUILD_FILE_SEPARATOR"] = "\\" |
|||
CONFIG["PATH_SEPARATOR"] = ";" |
|||
CONFIG["CFLAGS"] = "-MD -Zi -O2b2xg- -G6" |
|||
CONFIG["CPPFLAGS"] = "" |
|||
CONFIG["CXXFLAGS"] = "" |
|||
CONFIG["FFLAGS"] = "" |
|||
CONFIG["LDFLAGS"] = "" |
|||
CONFIG["LIBS"] = "oldnames.lib user32.lib advapi32.lib ws2_32.lib " |
|||
|
|||
# Set up paths |
|||
if ENV["MERLIN_ROOT"] then |
|||
# This is a dev environment. See http://wiki.github.com/ironruby/ironruby |
|||
TOPDIR = File.expand_path("bin/Debug", ENV["MERLIN_ROOT"]) |
|||
CONFIG["bindir"] = TOPDIR |
|||
CONFIG["libdir"] = File.expand_path("../External.LCA_RESTRICTED/Languages/Ruby/redist-libs", ENV["MERLIN_ROOT"]) |
|||
else |
|||
TOPDIR = File.dirname(__FILE__) + '/../../' |
|||
CONFIG["bindir"] = TOPDIR + "/bin" |
|||
CONFIG["libdir"] = TOPDIR + "/lib" |
|||
end |
|||
DESTDIR = TOPDIR && TOPDIR[/\A[a-z]:/i] || '' unless defined? DESTDIR |
|||
CONFIG["DESTDIR"] = DESTDIR |
|||
CONFIG["prefix"] = (TOPDIR || DESTDIR + "") |
|||
CONFIG["exec_prefix"] = "$(prefix)" |
|||
CONFIG["sbindir"] = "$(exec_prefix)/sbin" |
|||
CONFIG["libexecdir"] = "$(exec_prefix)/libexec" |
|||
CONFIG["datadir"] = "$(prefix)/share" |
|||
CONFIG["sysconfdir"] = "$(prefix)/etc" |
|||
CONFIG["sharedstatedir"] = "$(DESTDIR)/etc" |
|||
CONFIG["localstatedir"] = "$(DESTDIR)/var" |
|||
CONFIG["includedir"] = "$(prefix)/include" |
|||
CONFIG["infodir"] = "$(prefix)/info" |
|||
CONFIG["mandir"] = "$(prefix)/man" |
|||
CONFIG["rubylibdir"] = "$(libdir)/ruby/$(ruby_version)" |
|||
CONFIG["sitedir"] = "$(libdir)/ruby/site_ruby" |
|||
|
|||
CONFIG["oldincludedir"] = "/usr/include" |
|||
CONFIG["build"] = "i686-pc-mswin32" |
|||
CONFIG["build_alias"] = "i686-mswin32" |
|||
CONFIG["build_cpu"] = "i686" |
|||
CONFIG["build_vendor"] = "pc" |
|||
CONFIG["build_os"] = "mswin32" |
|||
CONFIG["host"] = "i686-pc-mswin32" |
|||
CONFIG["host_alias"] = "i686-mswin32" |
|||
CONFIG["host_cpu"] = "i686" |
|||
CONFIG["host_vendor"] = "pc" |
|||
CONFIG["host_os"] = "mswin32" |
|||
CONFIG["target"] = "i386-pc-mswin32" |
|||
CONFIG["target_alias"] = "i386-mswin32" |
|||
CONFIG["target_cpu"] = "i386" |
|||
CONFIG["target_vendor"] = "pc" |
|||
CONFIG["target_os"] = "mswin32" |
|||
CONFIG["CC"] = "cl -nologo" |
|||
CONFIG["CPP"] = "cl -nologo -E" |
|||
CONFIG["YACC"] = "byacc" |
|||
CONFIG["RANLIB"] = "" |
|||
CONFIG["AR"] = "lib -nologo" |
|||
CONFIG["ARFLAGS"] = "-machine:x86 -out:" |
|||
CONFIG["LN_S"] = "" |
|||
CONFIG["SET_MAKE"] = "" |
|||
CONFIG["CP"] = "copy > nul" |
|||
CONFIG["ALLOCA"] = "" |
|||
CONFIG["DEFAULT_KCODE"] = "" |
|||
CONFIG["OBJEXT"] = "obj" |
|||
CONFIG["XCFLAGS"] = "-DRUBY_EXPORT -I. -IC:/develop/win/ruby/ruby-1.8.6 -IC:/develop/win/ruby/ruby-1.8.6/missing" |
|||
CONFIG["XLDFLAGS"] = "-stack:0x2000000" |
|||
CONFIG["DLDFLAGS"] = "-link -incremental:no -debug -opt:ref -opt:icf -dll $(LIBPATH) -def:$(DEFFILE) -implib:$(*F:.so=)-$(arch).lib -pdb:$(*F:.so=)-$(arch).pdb" |
|||
CONFIG["ARCH_FLAG"] = "" |
|||
CONFIG["STATIC"] = "" |
|||
CONFIG["CCDLFLAGS"] = "" |
|||
CONFIG["LDSHARED"] = "cl -nologo -LD" |
|||
CONFIG["DLEXT"] = "so" |
|||
CONFIG["DLEXT2"] = "dll" |
|||
CONFIG["LIBEXT"] = "lib" |
|||
CONFIG["STRIP"] = "" |
|||
CONFIG["EXTSTATIC"] = "" |
|||
CONFIG["setup"] = "Setup" |
|||
CONFIG["MINIRUBY"] = ".\\miniruby.exe " |
|||
CONFIG["PREP"] = "miniruby.exe" |
|||
CONFIG["RUNRUBY"] = ".\\ruby.exe \"C:/develop/win/ruby/ruby-1.8.6/runruby.rb\" --extout=\".ext\" --" |
|||
CONFIG["EXTOUT"] = ".ext" |
|||
CONFIG["ARCHFILE"] = "" |
|||
CONFIG["RDOCTARGET"] = "install-nodoc" |
|||
CONFIG["LIBRUBY_LDSHARED"] = "cl -nologo -LD" |
|||
CONFIG["LIBRUBY_DLDFLAGS"] = " -def:msvcrt-ruby18.def" |
|||
CONFIG["rubyw_install_name"] = "rubyw" |
|||
CONFIG["RUBYW_INSTALL_NAME"] = "rubyw" |
|||
CONFIG["LIBRUBY_A"] = "$(RUBY_SO_NAME)-static.lib" |
|||
CONFIG["LIBRUBY_SO"] = "$(RUBY_SO_NAME).dll" |
|||
CONFIG["LIBRUBY_ALIASES"] = "" |
|||
CONFIG["LIBRUBY"] = "$(RUBY_SO_NAME).lib" |
|||
CONFIG["LIBRUBYARG"] = "$(LIBRUBYARG_SHARED)" |
|||
CONFIG["LIBRUBYARG_STATIC"] = "$(LIBRUBY_A)" |
|||
CONFIG["LIBRUBYARG_SHARED"] = "$(LIBRUBY)" |
|||
CONFIG["SOLIBS"] = "" |
|||
CONFIG["DLDLIBS"] = "" |
|||
CONFIG["ENABLE_SHARED"] = "yes" |
|||
CONFIG["OUTFLAG"] = "-Fe" |
|||
CONFIG["CPPOUTFILE"] = "-P" |
|||
CONFIG["LIBPATHFLAG"] = " -libpath:\"%s\"" |
|||
CONFIG["RPATHFLAG"] = "" |
|||
CONFIG["LIBARG"] = "%s.lib" |
|||
CONFIG["LINK_SO"] = "$(LDSHARED) -Fe$(@) $(OBJS) $(LIBS) $(LOCAL_LIBS) $(DLDFLAGS)" |
|||
CONFIG["COMPILE_C"] = "$(CC) $(INCFLAGS) $(CFLAGS) $(CPPFLAGS) -c -Tc$(<:\\=/)" |
|||
CONFIG["COMPILE_CXX"] = "$(CXX) $(INCFLAGS) $(CXXFLAGS) $(CPPFLAGS) -c -Tp$(<:\\=/)" |
|||
CONFIG["COMPILE_RULES"] = "{$(srcdir)}.%s{}.%s: {$(topdir)}.%s{}.%s: {$(hdrdir)}.%s{}.%s: .%s.%s:" |
|||
CONFIG["RULE_SUBST"] = "{.;$(srcdir);$(topdir);$(hdrdir)}%s" |
|||
CONFIG["TRY_LINK"] = "$(CC) -Feconftest $(INCFLAGS) -I$(hdrdir) $(CPPFLAGS) $(CFLAGS) $(src) $(LOCAL_LIBS) $(LIBS) -link $(LDFLAGS) $(LIBPATH) $(XLDFLAGS)" |
|||
CONFIG["COMMON_LIBS"] = "m" |
|||
CONFIG["COMMON_MACROS"] = "WIN32_LEAN_AND_MEAN" |
|||
CONFIG["COMMON_HEADERS"] = "winsock2.h windows.h" |
|||
CONFIG["DISTCLEANFILES"] = "vc*.pdb" |
|||
CONFIG["EXPORT_PREFIX"] = " " |
|||
CONFIG["arch"] = "i386-mswin32" |
|||
CONFIG["sitearch"] = "i386-msvcrt" |
|||
CONFIG["configure_args"] = "--with-make-prog=nmake --enable-shared --with-winsock2" |
|||
CONFIG["ruby_version"] = "$(MAJOR).$(MINOR)" |
|||
CONFIG["archdir"] = "$(rubylibdir)/$(arch)" |
|||
CONFIG["sitelibdir"] = "$(sitedir)/$(ruby_version)" |
|||
CONFIG["sitearchdir"] = "$(sitelibdir)/$(sitearch)" |
|||
CONFIG["topdir"] = File.dirname(__FILE__) |
|||
MAKEFILE_CONFIG = {} |
|||
CONFIG.each{|k,v| MAKEFILE_CONFIG[k] = v.dup} |
|||
def Config::expand(val, config = CONFIG) |
|||
val.gsub!(/\$\$|\$\(([^()]+)\)|\$\{([^{}]+)\}/) do |var| |
|||
if !(v = $1 || $2) |
|||
'$' |
|||
elsif key = config[v = v[/\A[^:]+(?=(?::(.*?)=(.*))?\z)/]] |
|||
pat, sub = $1, $2 |
|||
config[v] = false |
|||
Config::expand(key, config) |
|||
config[v] = key |
|||
key = key.gsub(/#{Regexp.quote(pat)}(?=\s|\z)/n) {sub} if pat |
|||
key |
|||
else |
|||
var |
|||
end |
|||
end |
|||
val |
|||
end |
|||
CONFIG.each_value do |val| |
|||
Config::expand(val) |
|||
end |
|||
end |
|||
RbConfig = Config # compatibility for ruby-1.9 |
|||
CROSS_COMPILING = nil unless defined? CROSS_COMPILING |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Sockets' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.StringIO' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.StringScanner' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
#placeholder for either throwing an error, or implementing a readline library |
|||
@ -0,0 +1 @@ |
|||
require 'System, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089' |
|||
@ -0,0 +1,281 @@ |
|||
require 'hacks' |
|||
require 'test/unit/testcase' |
|||
require 'test/unit/autorunner' |
|||
|
|||
module Test # :nodoc: |
|||
# |
|||
# = Test::Unit - Ruby Unit Testing Framework |
|||
# |
|||
# == Introduction |
|||
# |
|||
# Unit testing is making waves all over the place, largely due to the |
|||
# fact that it is a core practice of XP. While XP is great, unit testing |
|||
# has been around for a long time and has always been a good idea. One |
|||
# of the keys to good unit testing, though, is not just writing tests, |
|||
# but having tests. What's the difference? Well, if you just _write_ a |
|||
# test and throw it away, you have no guarantee that something won't |
|||
# change later which breaks your code. If, on the other hand, you _have_ |
|||
# tests (obviously you have to write them first), and run them as often |
|||
# as possible, you slowly build up a wall of things that cannot break |
|||
# without you immediately knowing about it. This is when unit testing |
|||
# hits its peak usefulness. |
|||
# |
|||
# Enter Test::Unit, a framework for unit testing in Ruby, helping you to |
|||
# design, debug and evaluate your code by making it easy to write and |
|||
# have tests for it. |
|||
# |
|||
# |
|||
# == Notes |
|||
# |
|||
# Test::Unit has grown out of and superceded Lapidary. |
|||
# |
|||
# |
|||
# == Feedback |
|||
# |
|||
# I like (and do my best to practice) XP, so I value early releases, |
|||
# user feedback, and clean, simple, expressive code. There is always |
|||
# room for improvement in everything I do, and Test::Unit is no |
|||
# exception. Please, let me know what you think of Test::Unit as it |
|||
# stands, and what you'd like to see expanded/changed/improved/etc. If |
|||
# you find a bug, let me know ASAP; one good way to let me know what the |
|||
# bug is is to submit a new test that catches it :-) Also, I'd love to |
|||
# hear about any successes you have with Test::Unit, and any |
|||
# documentation you might add will be greatly appreciated. My contact |
|||
# info is below. |
|||
# |
|||
# |
|||
# == Contact Information |
|||
# |
|||
# A lot of discussion happens about Ruby in general on the ruby-talk |
|||
# mailing list (http://www.ruby-lang.org/en/ml.html), and you can ask |
|||
# any questions you might have there. I monitor the list, as do many |
|||
# other helpful Rubyists, and you're sure to get a quick answer. Of |
|||
# course, you're also welcome to email me (Nathaniel Talbott) directly |
|||
# at mailto:testunit@talbott.ws, and I'll do my best to help you out. |
|||
# |
|||
# |
|||
# == Credits |
|||
# |
|||
# I'd like to thank... |
|||
# |
|||
# Matz, for a great language! |
|||
# |
|||
# Masaki Suketa, for his work on RubyUnit, which filled a vital need in |
|||
# the Ruby world for a very long time. I'm also grateful for his help in |
|||
# polishing Test::Unit and getting the RubyUnit compatibility layer |
|||
# right. His graciousness in allowing Test::Unit to supercede RubyUnit |
|||
# continues to be a challenge to me to be more willing to defer my own |
|||
# rights. |
|||
# |
|||
# Ken McKinlay, for his interest and work on unit testing, and for his |
|||
# willingness to dialog about it. He was also a great help in pointing |
|||
# out some of the holes in the RubyUnit compatibility layer. |
|||
# |
|||
# Dave Thomas, for the original idea that led to the extremely simple |
|||
# "require 'test/unit'", plus his code to improve it even more by |
|||
# allowing the selection of tests from the command-line. Also, without |
|||
# RDoc, the documentation for Test::Unit would stink a lot more than it |
|||
# does now. |
|||
# |
|||
# Everyone who's helped out with bug reports, feature ideas, |
|||
# encouragement to continue, etc. It's a real privilege to be a part of |
|||
# the Ruby community. |
|||
# |
|||
# The guys at RoleModel Software, for putting up with me repeating, "But |
|||
# this would be so much easier in Ruby!" whenever we're coding in Java. |
|||
# |
|||
# My Creator, for giving me life, and giving it more abundantly. |
|||
# |
|||
# |
|||
# == License |
|||
# |
|||
# Test::Unit is copyright (c) 2000-2003 Nathaniel Talbott. It is free |
|||
# software, and is distributed under the Ruby license. See the COPYING |
|||
# file in the standard Ruby distribution for details. |
|||
# |
|||
# |
|||
# == Warranty |
|||
# |
|||
# This software is provided "as is" and without any express or |
|||
# implied warranties, including, without limitation, the implied |
|||
# warranties of merchantibility and fitness for a particular |
|||
# purpose. |
|||
# |
|||
# |
|||
# == Author |
|||
# |
|||
# Nathaniel Talbott. |
|||
# Copyright (c) 2000-2003, Nathaniel Talbott |
|||
# |
|||
# ---- |
|||
# |
|||
# = Usage |
|||
# |
|||
# The general idea behind unit testing is that you write a _test_ |
|||
# _method_ that makes certain _assertions_ about your code, working |
|||
# against a _test_ _fixture_. A bunch of these _test_ _methods_ are |
|||
# bundled up into a _test_ _suite_ and can be run any time the |
|||
# developer wants. The results of a run are gathered in a _test_ |
|||
# _result_ and displayed to the user through some UI. So, lets break |
|||
# this down and see how Test::Unit provides each of these necessary |
|||
# pieces. |
|||
# |
|||
# |
|||
# == Assertions |
|||
# |
|||
# These are the heart of the framework. Think of an assertion as a |
|||
# statement of expected outcome, i.e. "I assert that x should be equal |
|||
# to y". If, when the assertion is executed, it turns out to be |
|||
# correct, nothing happens, and life is good. If, on the other hand, |
|||
# your assertion turns out to be false, an error is propagated with |
|||
# pertinent information so that you can go back and make your |
|||
# assertion succeed, and, once again, life is good. For an explanation |
|||
# of the current assertions, see Test::Unit::Assertions. |
|||
# |
|||
# |
|||
# == Test Method & Test Fixture |
|||
# |
|||
# Obviously, these assertions have to be called within a context that |
|||
# knows about them and can do something meaningful with their |
|||
# pass/fail value. Also, it's handy to collect a bunch of related |
|||
# tests, each test represented by a method, into a common test class |
|||
# that knows how to run them. The tests will be in a separate class |
|||
# from the code they're testing for a couple of reasons. First of all, |
|||
# it allows your code to stay uncluttered with test code, making it |
|||
# easier to maintain. Second, it allows the tests to be stripped out |
|||
# for deployment, since they're really there for you, the developer, |
|||
# and your users don't need them. Third, and most importantly, it |
|||
# allows you to set up a common test fixture for your tests to run |
|||
# against. |
|||
# |
|||
# What's a test fixture? Well, tests do not live in a vacuum; rather, |
|||
# they're run against the code they are testing. Often, a collection |
|||
# of tests will run against a common set of data, also called a |
|||
# fixture. If they're all bundled into the same test class, they can |
|||
# all share the setting up and tearing down of that data, eliminating |
|||
# unnecessary duplication and making it much easier to add related |
|||
# tests. |
|||
# |
|||
# Test::Unit::TestCase wraps up a collection of test methods together |
|||
# and allows you to easily set up and tear down the same test fixture |
|||
# for each test. This is done by overriding #setup and/or #teardown, |
|||
# which will be called before and after each test method that is |
|||
# run. The TestCase also knows how to collect the results of your |
|||
# assertions into a Test::Unit::TestResult, which can then be reported |
|||
# back to you... but I'm getting ahead of myself. To write a test, |
|||
# follow these steps: |
|||
# |
|||
# * Make sure Test::Unit is in your library path. |
|||
# * require 'test/unit' in your test script. |
|||
# * Create a class that subclasses Test::Unit::TestCase. |
|||
# * Add a method that begins with "test" to your class. |
|||
# * Make assertions in your test method. |
|||
# * Optionally define #setup and/or #teardown to set up and/or tear |
|||
# down your common test fixture. |
|||
# * You can now run your test as you would any other Ruby |
|||
# script... try it and see! |
|||
# |
|||
# A really simple test might look like this (#setup and #teardown are |
|||
# commented out to indicate that they are completely optional): |
|||
# |
|||
# require 'test/unit' |
|||
# |
|||
# class TC_MyTest < Test::Unit::TestCase |
|||
# # def setup |
|||
# # end |
|||
# |
|||
# # def teardown |
|||
# # end |
|||
# |
|||
# def test_fail |
|||
# assert(false, 'Assertion was false.') |
|||
# end |
|||
# end |
|||
# |
|||
# |
|||
# == Test Runners |
|||
# |
|||
# So, now you have this great test class, but you still need a way to |
|||
# run it and view any failures that occur during the run. This is |
|||
# where Test::Unit::UI::Console::TestRunner (and others, such as |
|||
# Test::Unit::UI::GTK::TestRunner) comes into play. The console test |
|||
# runner is automatically invoked for you if you require 'test/unit' |
|||
# and simply run the file. To use another runner, or to manually |
|||
# invoke a runner, simply call its run class method and pass in an |
|||
# object that responds to the suite message with a |
|||
# Test::Unit::TestSuite. This can be as simple as passing in your |
|||
# TestCase class (which has a class suite method). It might look |
|||
# something like this: |
|||
# |
|||
# require 'test/unit/ui/console/testrunner' |
|||
# Test::Unit::UI::Console::TestRunner.run(TC_MyTest) |
|||
# |
|||
# |
|||
# == Test Suite |
|||
# |
|||
# As more and more unit tests accumulate for a given project, it |
|||
# becomes a real drag running them one at a time, and it also |
|||
# introduces the potential to overlook a failing test because you |
|||
# forget to run it. Suddenly it becomes very handy that the |
|||
# TestRunners can take any object that returns a Test::Unit::TestSuite |
|||
# in response to a suite method. The TestSuite can, in turn, contain |
|||
# other TestSuites or individual tests (typically created by a |
|||
# TestCase). In other words, you can easily wrap up a group of |
|||
# TestCases and TestSuites like this: |
|||
# |
|||
# require 'test/unit/testsuite' |
|||
# require 'tc_myfirsttests' |
|||
# require 'tc_moretestsbyme' |
|||
# require 'ts_anothersetoftests' |
|||
# |
|||
# class TS_MyTests |
|||
# def self.suite |
|||
# suite = Test::Unit::TestSuite.new |
|||
# suite << TC_MyFirstTests.suite |
|||
# suite << TC_MoreTestsByMe.suite |
|||
# suite << TS_AnotherSetOfTests.suite |
|||
# return suite |
|||
# end |
|||
# end |
|||
# Test::Unit::UI::Console::TestRunner.run(TS_MyTests) |
|||
# |
|||
# Now, this is a bit cumbersome, so Test::Unit does a little bit more |
|||
# for you, by wrapping these up automatically when you require |
|||
# 'test/unit'. What does this mean? It means you could write the above |
|||
# test case like this instead: |
|||
# |
|||
# require 'test/unit' |
|||
# require 'tc_myfirsttests' |
|||
# require 'tc_moretestsbyme' |
|||
# require 'ts_anothersetoftests' |
|||
# |
|||
# Test::Unit is smart enough to find all the test cases existing in |
|||
# the ObjectSpace and wrap them up into a suite for you. It then runs |
|||
# the dynamic suite using the console TestRunner. |
|||
# |
|||
# |
|||
# == Questions? |
|||
# |
|||
# I'd really like to get feedback from all levels of Ruby |
|||
# practitioners about typos, grammatical errors, unclear statements, |
|||
# missing points, etc., in this document (or any other). |
|||
# |
|||
|
|||
module Unit |
|||
# If set to false Test::Unit will not automatically run at exit. |
|||
def self.run=(flag) |
|||
@run = flag |
|||
end |
|||
|
|||
# Automatically run tests at exit? |
|||
def self.run? |
|||
@run ||= false |
|||
end |
|||
end |
|||
end |
|||
|
|||
at_exit do |
|||
unless $! || Test::Unit.run? |
|||
exit Test::Unit::AutoRunner.run |
|||
end |
|||
end |
|||
@ -0,0 +1,217 @@ |
|||
require 'test/unit' |
|||
require 'test/unit/ui/testrunnerutilities' |
|||
require 'optparse' |
|||
|
|||
module Test |
|||
module Unit |
|||
class AutoRunner |
|||
def self.run(force_standalone=false, default_dir=nil, argv=ARGV, &block) |
|||
r = new(force_standalone || standalone?, &block) |
|||
r.base = default_dir |
|||
r.process_args(argv) |
|||
r.run |
|||
end |
|||
|
|||
def self.standalone? |
|||
return false unless("-e" == $0) |
|||
return TestCase.subclasses.length == 0 |
|||
end |
|||
|
|||
RUNNERS = { |
|||
:console => proc do |r| |
|||
require 'test/unit/ui/console/testrunner' |
|||
Test::Unit::UI::Console::TestRunner |
|||
end, |
|||
:gtk => proc do |r| |
|||
require 'test/unit/ui/gtk/testrunner' |
|||
Test::Unit::UI::GTK::TestRunner |
|||
end, |
|||
:gtk2 => proc do |r| |
|||
require 'test/unit/ui/gtk2/testrunner' |
|||
Test::Unit::UI::GTK2::TestRunner |
|||
end, |
|||
:fox => proc do |r| |
|||
require 'test/unit/ui/fox/testrunner' |
|||
Test::Unit::UI::Fox::TestRunner |
|||
end, |
|||
:tk => proc do |r| |
|||
require 'test/unit/ui/tk/testrunner' |
|||
Test::Unit::UI::Tk::TestRunner |
|||
end, |
|||
} |
|||
|
|||
OUTPUT_LEVELS = [ |
|||
[:silent, UI::SILENT], |
|||
[:progress, UI::PROGRESS_ONLY], |
|||
[:normal, UI::NORMAL], |
|||
[:verbose, UI::VERBOSE], |
|||
] |
|||
|
|||
COLLECTORS = { |
|||
:objectspace => proc do |r| |
|||
require 'test/unit/collector/objectspace' |
|||
c = Collector::ObjectSpace.new(TestCase.subclasses) |
|||
c.filter = r.filters |
|||
c.collect($0.sub(/\.rb\Z/, '')) |
|||
end, |
|||
:dir => proc do |r| |
|||
require 'test/unit/collector/dir' |
|||
c = Collector::Dir.new |
|||
c.filter = r.filters |
|||
c.pattern.concat(r.pattern) if(r.pattern) |
|||
c.exclude.concat(r.exclude) if(r.exclude) |
|||
c.base = r.base |
|||
$:.push(r.base) if r.base |
|||
c.collect(*(r.to_run.empty? ? ['.'] : r.to_run)) |
|||
end, |
|||
} |
|||
|
|||
attr_reader :suite |
|||
attr_accessor :output_level, :filters, :to_run, :pattern, :exclude, :base, :workdir |
|||
attr_writer :runner, :collector |
|||
|
|||
def initialize(standalone) |
|||
Unit.run = true |
|||
@standalone = standalone |
|||
@runner = RUNNERS[:console] |
|||
@collector = COLLECTORS[(standalone ? :dir : :objectspace)] |
|||
@filters = [] |
|||
@to_run = [] |
|||
@output_level = UI::NORMAL |
|||
@workdir = nil |
|||
yield(self) if(block_given?) |
|||
end |
|||
|
|||
def process_args(args = ARGV) |
|||
begin |
|||
options.order!(args) {|arg| @to_run << arg} |
|||
rescue OptionParser::ParseError => e |
|||
puts e |
|||
puts options |
|||
$! = nil |
|||
abort |
|||
else |
|||
@filters << proc{false} unless(@filters.empty?) |
|||
end |
|||
not @to_run.empty? |
|||
end |
|||
|
|||
def options |
|||
@options ||= OptionParser.new do |o| |
|||
o.banner = "Test::Unit automatic runner." |
|||
o.banner << "\nUsage: #{$0} [options] [-- untouched arguments]" |
|||
|
|||
o.on |
|||
o.on('-r', '--runner=RUNNER', RUNNERS, |
|||
"Use the given RUNNER.", |
|||
"(" + keyword_display(RUNNERS) + ")") do |r| |
|||
@runner = r |
|||
end |
|||
|
|||
if(@standalone) |
|||
o.on('-b', '--basedir=DIR', "Base directory of test suites.") do |b| |
|||
@base = b |
|||
end |
|||
|
|||
o.on('-w', '--workdir=DIR', "Working directory to run tests.") do |w| |
|||
@workdir = w |
|||
end |
|||
|
|||
o.on('-a', '--add=TORUN', Array, |
|||
"Add TORUN to the list of things to run;", |
|||
"can be a file or a directory.") do |a| |
|||
@to_run.concat(a) |
|||
end |
|||
|
|||
@pattern = [] |
|||
o.on('-p', '--pattern=PATTERN', Regexp, |
|||
"Match files to collect against PATTERN.") do |e| |
|||
@pattern << e |
|||
end |
|||
|
|||
@exclude = [] |
|||
o.on('-x', '--exclude=PATTERN', Regexp, |
|||
"Ignore files to collect against PATTERN.") do |e| |
|||
@exclude << e |
|||
end |
|||
end |
|||
|
|||
o.on('-n', '--name=NAME', String, |
|||
"Runs tests matching NAME.", |
|||
"(patterns may be used).") do |n| |
|||
n = (%r{\A/(.*)/\Z} =~ n ? Regexp.new($1) : n) |
|||
case n |
|||
when Regexp |
|||
@filters << proc{|t| n =~ t.method_name ? true : nil} |
|||
else |
|||
@filters << proc{|t| n == t.method_name ? true : nil} |
|||
end |
|||
end |
|||
|
|||
o.on('-t', '--testcase=TESTCASE', String, |
|||
"Runs tests in TestCases matching TESTCASE.", |
|||
"(patterns may be used).") do |n| |
|||
n = (%r{\A/(.*)/\Z} =~ n ? Regexp.new($1) : n) |
|||
case n |
|||
when Regexp |
|||
@filters << proc{|t| n =~ t.class.name ? true : nil} |
|||
else |
|||
@filters << proc{|t| n == t.class.name ? true : nil} |
|||
end |
|||
end |
|||
|
|||
o.on('-I', "--load-path=DIR[#{File::PATH_SEPARATOR}DIR...]", |
|||
"Appends directory list to $LOAD_PATH.") do |dirs| |
|||
$LOAD_PATH.concat(dirs.split(File::PATH_SEPARATOR)) |
|||
end |
|||
|
|||
o.on('-v', '--verbose=[LEVEL]', OUTPUT_LEVELS, |
|||
"Set the output level (default is verbose).", |
|||
"(" + keyword_display(OUTPUT_LEVELS) + ")") do |l| |
|||
@output_level = l || UI::VERBOSE |
|||
end |
|||
|
|||
o.on('--', |
|||
"Stop processing options so that the", |
|||
"remaining options will be passed to the", |
|||
"test."){o.terminate} |
|||
|
|||
o.on('-h', '--help', 'Display this help.'){puts o; exit} |
|||
|
|||
o.on_tail |
|||
o.on_tail('Deprecated options:') |
|||
|
|||
o.on_tail('--console', 'Console runner (use --runner).') do |
|||
warn("Deprecated option (--console).") |
|||
@runner = RUNNERS[:console] |
|||
end |
|||
|
|||
o.on_tail('--gtk', 'GTK runner (use --runner).') do |
|||
warn("Deprecated option (--gtk).") |
|||
@runner = RUNNERS[:gtk] |
|||
end |
|||
|
|||
o.on_tail('--fox', 'Fox runner (use --runner).') do |
|||
warn("Deprecated option (--fox).") |
|||
@runner = RUNNERS[:fox] |
|||
end |
|||
|
|||
o.on_tail |
|||
end |
|||
end |
|||
|
|||
def keyword_display(array) |
|||
list = array.collect {|e, *| e.to_s} |
|||
Array === array or list.sort! |
|||
list.collect {|e| e.sub(/^(.)([A-Za-z]+)(?=\w*$)/, '\\1[\\2]')}.join(", ") |
|||
end |
|||
|
|||
def run |
|||
@suite = @collector[self] |
|||
result = @runner[self] or return false |
|||
Dir.chdir(@workdir) if @workdir |
|||
result.run(@suite, @output_level).passed? |
|||
end |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,162 @@ |
|||
#-- |
|||
# |
|||
# Author:: Nathaniel Talbott. |
|||
# Copyright:: Copyright (c) 2000-2003 Nathaniel Talbott. All rights reserved. |
|||
# License:: Ruby license. |
|||
|
|||
require 'test/unit/assertions' |
|||
require 'test/unit/failure' |
|||
require 'test/unit/error' |
|||
require 'test/unit/testsuite' |
|||
require 'test/unit/assertionfailederror' |
|||
require 'test/unit/util/backtracefilter' |
|||
require File.dirname(__FILE__) + '/../../hacks' |
|||
|
|||
module Test |
|||
module Unit |
|||
|
|||
# Ties everything together. If you subclass and add your own |
|||
# test methods, it takes care of making them into tests and |
|||
# wrapping those tests into a suite. It also does the |
|||
# nitty-gritty of actually running an individual test and |
|||
# collecting its results into a Test::Unit::TestResult object. |
|||
class TestCase |
|||
include Assertions |
|||
include Util::BacktraceFilter |
|||
|
|||
attr_reader :method_name |
|||
|
|||
STARTED = name + "::STARTED" |
|||
FINISHED = name + "::FINISHED" |
|||
|
|||
## |
|||
# These exceptions are not caught by #run. |
|||
|
|||
PASSTHROUGH_EXCEPTIONS = [NoMemoryError, SignalException, Interrupt, |
|||
SystemExit] |
|||
|
|||
# Creates a new instance of the fixture for running the |
|||
# test represented by test_method_name. |
|||
def initialize(test_method_name) |
|||
unless(respond_to?(test_method_name) and |
|||
(method(test_method_name).arity == 0 || |
|||
method(test_method_name).arity == -1)) |
|||
throw :invalid_test |
|||
end |
|||
@method_name = test_method_name |
|||
@test_passed = true |
|||
end |
|||
|
|||
# Rolls up all of the test* methods in the fixture into |
|||
# one suite, creating a new instance of the fixture for |
|||
# each method. |
|||
def self.suite |
|||
method_names = public_instance_methods(true) |
|||
tests = method_names.delete_if {|method_name| method_name !~ /^test./} |
|||
suite = TestSuite.new(name) |
|||
tests.sort.each do |
|||
|test| |
|||
catch(:invalid_test) do |
|||
suite << new(test) |
|||
end |
|||
end |
|||
if (suite.empty?) |
|||
catch(:invalid_test) do |
|||
suite << new("default_test") |
|||
end |
|||
end |
|||
return suite |
|||
end |
|||
|
|||
# Runs the individual test method represented by this |
|||
# instance of the fixture, collecting statistics, failures |
|||
# and errors in result. |
|||
def run(result) |
|||
yield(STARTED, name) |
|||
@_result = result |
|||
begin |
|||
setup |
|||
__send__(@method_name) |
|||
rescue AssertionFailedError => e |
|||
add_failure(e.message, e.backtrace) |
|||
rescue Exception |
|||
raise if PASSTHROUGH_EXCEPTIONS.include? $!.class |
|||
add_error($!) |
|||
ensure |
|||
begin |
|||
teardown |
|||
rescue AssertionFailedError => e |
|||
add_failure(e.message, e.backtrace) |
|||
rescue Exception |
|||
raise if PASSTHROUGH_EXCEPTIONS.include? $!.class |
|||
add_error($!) |
|||
end |
|||
end |
|||
result.add_run |
|||
yield(FINISHED, name) |
|||
end |
|||
|
|||
# Called before every test method runs. Can be used |
|||
# to set up fixture information. |
|||
def setup |
|||
end |
|||
|
|||
# Called after every test method runs. Can be used to tear |
|||
# down fixture information. |
|||
def teardown |
|||
end |
|||
|
|||
def default_test |
|||
flunk("No tests were specified") |
|||
end |
|||
|
|||
# Returns whether this individual test passed or |
|||
# not. Primarily for use in teardown so that artifacts |
|||
# can be left behind if the test fails. |
|||
def passed? |
|||
return @test_passed |
|||
end |
|||
private :passed? |
|||
|
|||
def size |
|||
1 |
|||
end |
|||
|
|||
def add_assertion |
|||
@_result.add_assertion |
|||
end |
|||
private :add_assertion |
|||
|
|||
def add_failure(message, all_locations=caller()) |
|||
@test_passed = false |
|||
@_result.add_failure(Failure.new(name, filter_backtrace(all_locations), message)) |
|||
end |
|||
private :add_failure |
|||
|
|||
def add_error(exception) |
|||
@test_passed = false |
|||
@_result.add_error(Error.new(name, exception)) |
|||
end |
|||
private :add_error |
|||
|
|||
# Returns a human-readable name for the specific test that |
|||
# this instance of TestCase represents. |
|||
def name |
|||
"#{@method_name}(#{self.class.name})" |
|||
end |
|||
|
|||
# Overridden to return #name. |
|||
def to_s |
|||
name |
|||
end |
|||
|
|||
# It's handy to be able to compare TestCase instances. |
|||
def ==(other) |
|||
return false unless(other.kind_of?(self.class)) |
|||
return false unless(@method_name == other.method_name) |
|||
self.class == other.class |
|||
end |
|||
end |
|||
TestCase.extend ::SubclassTracking |
|||
end |
|||
end |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Threading' |
|||
@ -0,0 +1,38 @@ |
|||
# |
|||
# tmpdir - retrieve temporary directory path |
|||
# |
|||
# $Id: tmpdir.rb 11708 2007-02-12 23:01:19Z shyouhei $ |
|||
# |
|||
|
|||
require 'mscorlib' |
|||
|
|||
class Dir |
|||
|
|||
begin |
|||
@@systmpdir = System::IO::Path.get_temp_path |
|||
rescue |
|||
@@systmpdir = nil |
|||
end |
|||
|
|||
private |
|||
|
|||
## |
|||
# Returns the operating system's temporary file path. |
|||
|
|||
def Dir::tmpdir |
|||
tmp = '.' |
|||
if $SAFE > 0 and @@systmpdir |
|||
tmp = @@systmpdir |
|||
else |
|||
for dir in [ENV['TMPDIR'], ENV['TMP'], ENV['TEMP'], |
|||
ENV['USERPROFILE'], @@systmpdir, '/tmp'] |
|||
if dir and File.directory?(dir) and File.writable?(dir) |
|||
tmp = dir |
|||
break |
|||
end |
|||
end |
|||
end |
|||
File.expand_path(tmp) |
|||
end |
|||
end |
|||
|
|||
@ -0,0 +1,18 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
require 'stringio' |
|||
require 'date' |
|||
load_assembly 'IronRuby.Libraries.Yaml', 'IronRuby.StandardLibrary.Yaml' |
|||
@ -0,0 +1,16 @@ |
|||
# **************************************************************************** |
|||
# |
|||
# Copyright (c) Microsoft Corporation. |
|||
# |
|||
# This source code is subject to terms and conditions of the Microsoft Public License. A |
|||
# copy of the license can be found in the License.html file at the root of this distribution. If |
|||
# you cannot locate the Microsoft Public License, please send an email to |
|||
# ironruby@microsoft.com. By using this source code in any fashion, you are agreeing to be bound |
|||
# by the terms of the Microsoft Public License. |
|||
# |
|||
# You must not remove this notice, or any other, from this software. |
|||
# |
|||
# |
|||
# **************************************************************************** |
|||
|
|||
load_assembly 'IronRuby.Libraries', 'IronRuby.StandardLibrary.Zlib' |
|||
@ -0,0 +1,155 @@ |
|||
# Include the English library file in a Ruby script, and you can |
|||
# reference the global variables such as \VAR{\$\_} using less |
|||
# cryptic names, listed in the following table.% \vref{tab:english}. |
|||
# |
|||
# Without 'English': |
|||
# |
|||
# $\ = ' -- ' |
|||
# "waterbuffalo" =~ /buff/ |
|||
# print $", $', $$, "\n" |
|||
# |
|||
# With English: |
|||
# |
|||
# require "English" |
|||
# |
|||
# $OUTPUT_FIELD_SEPARATOR = ' -- ' |
|||
# "waterbuffalo" =~ /buff/ |
|||
# print $LOADED_FEATURES, $POSTMATCH, $PID, "\n" |
|||
|
|||
|
|||
# The exception object passed to +raise+. |
|||
alias $ERROR_INFO $! |
|||
|
|||
# The stack backtrace generated by the last |
|||
# exception. <tt>See Kernel.caller</tt> for details. Thread local. |
|||
alias $ERROR_POSITION $@ |
|||
|
|||
# The default separator pattern used by <tt>String.split</tt>. May be |
|||
# set from the command line using the <tt>-F</tt> flag. |
|||
alias $FS $; |
|||
|
|||
# The default separator pattern used by <tt>String.split</tt>. May be |
|||
# set from the command line using the <tt>-F</tt> flag. |
|||
alias $FIELD_SEPARATOR $; |
|||
|
|||
# The separator string output between the parameters to methods such |
|||
# as <tt>Kernel.print</tt> and <tt>Array.join</tt>. Defaults to +nil+, |
|||
# which adds no text. |
|||
alias $OFS $, |
|||
|
|||
# The separator string output between the parameters to methods such |
|||
# as <tt>Kernel.print</tt> and <tt>Array.join</tt>. Defaults to +nil+, |
|||
# which adds no text. |
|||
alias $OUTPUT_FIELD_SEPARATOR $, |
|||
|
|||
# The input record separator (newline by default). This is the value |
|||
# that routines such as <tt>Kernel.gets</tt> use to determine record |
|||
# boundaries. If set to +nil+, +gets+ will read the entire file. |
|||
alias $RS $/ |
|||
|
|||
# The input record separator (newline by default). This is the value |
|||
# that routines such as <tt>Kernel.gets</tt> use to determine record |
|||
# boundaries. If set to +nil+, +gets+ will read the entire file. |
|||
alias $INPUT_RECORD_SEPARATOR $/ |
|||
|
|||
# The string appended to the output of every call to methods such as |
|||
# <tt>Kernel.print</tt> and <tt>IO.write</tt>. The default value is |
|||
# +nil+. |
|||
alias $ORS $\ |
|||
|
|||
# The string appended to the output of every call to methods such as |
|||
# <tt>Kernel.print</tt> and <tt>IO.write</tt>. The default value is |
|||
# +nil+. |
|||
alias $OUTPUT_RECORD_SEPARATOR $\ |
|||
|
|||
# The number of the last line read from the current input file. |
|||
alias $INPUT_LINE_NUMBER $. |
|||
|
|||
# The number of the last line read from the current input file. |
|||
alias $NR $. |
|||
|
|||
# The last line read by <tt>Kernel.gets</tt> or |
|||
# <tt>Kernel.readline</tt>. Many string-related functions in the |
|||
# +Kernel+ module operate on <tt>$_</tt> by default. The variable is |
|||
# local to the current scope. Thread local. |
|||
alias $LAST_READ_LINE $_ |
|||
|
|||
# The destination of output for <tt>Kernel.print</tt> |
|||
# and <tt>Kernel.printf</tt>. The default value is |
|||
# <tt>$stdout</tt>. |
|||
alias $DEFAULT_OUTPUT $> |
|||
|
|||
# An object that provides access to the concatenation |
|||
# of the contents of all the files |
|||
# given as command-line arguments, or <tt>$stdin</tt> |
|||
# (in the case where there are no |
|||
# arguments). <tt>$<</tt> supports methods similar to a |
|||
# +File+ object: |
|||
# +inmode+, +close+, |
|||
# <tt>closed?</tt>, +each+, |
|||
# <tt>each_byte</tt>, <tt>each_line</tt>, |
|||
# +eof+, <tt>eof?</tt>, +file+, |
|||
# +filename+, +fileno+, |
|||
# +getc+, +gets+, +lineno+, |
|||
# <tt>lineno=</tt>, +path+, |
|||
# +pos+, <tt>pos=</tt>, |
|||
# +read+, +readchar+, |
|||
# +readline+, +readlines+, |
|||
# +rewind+, +seek+, +skip+, |
|||
# +tell+, <tt>to_a</tt>, <tt>to_i</tt>, |
|||
# <tt>to_io</tt>, <tt>to_s</tt>, along with the |
|||
# methods in +Enumerable+. The method +file+ |
|||
# returns a +File+ object for the file currently |
|||
# being read. This may change as <tt>$<</tt> reads |
|||
# through the files on the command line. Read only. |
|||
alias $DEFAULT_INPUT $< |
|||
|
|||
# The process number of the program being executed. Read only. |
|||
alias $PID $$ |
|||
|
|||
# The process number of the program being executed. Read only. |
|||
alias $PROCESS_ID $$ |
|||
|
|||
# The exit status of the last child process to terminate. Read |
|||
# only. Thread local. |
|||
alias $CHILD_STATUS $? |
|||
|
|||
# A +MatchData+ object that encapsulates the results of a successful |
|||
# pattern match. The variables <tt>$&</tt>, <tt>$`</tt>, <tt>$'</tt>, |
|||
# and <tt>$1</tt> to <tt>$9</tt> are all derived from |
|||
# <tt>$~</tt>. Assigning to <tt>$~</tt> changes the values of these |
|||
# derived variables. This variable is local to the current |
|||
# scope. Thread local. |
|||
alias $LAST_MATCH_INFO $~ |
|||
|
|||
# If set to any value apart from +nil+ or +false+, all pattern matches |
|||
# will be case insensitive, string comparisons will ignore case, and |
|||
# string hash values will be case insensitive. Deprecated |
|||
alias $IGNORECASE $= |
|||
|
|||
# An array of strings containing the command-line |
|||
# options from the invocation of the program. Options |
|||
# used by the Ruby interpreter will have been |
|||
# removed. Read only. Also known simply as +ARGV+. |
|||
alias $ARGV $* |
|||
|
|||
# The string matched by the last successful pattern |
|||
# match. This variable is local to the current |
|||
# scope. Read only. Thread local. |
|||
alias $MATCH $& |
|||
|
|||
# The string preceding the match in the last |
|||
# successful pattern match. This variable is local to |
|||
# the current scope. Read only. Thread local. |
|||
alias $PREMATCH $` |
|||
|
|||
# The string following the match in the last |
|||
# successful pattern match. This variable is local to |
|||
# the current scope. Read only. Thread local. |
|||
alias $POSTMATCH $' |
|||
|
|||
# The contents of the highest-numbered group matched in the last |
|||
# successful pattern match. Thus, in <tt>"cat" =~ /(c|a)(t|z)/</tt>, |
|||
# <tt>$+</tt> will be set to "t". This variable is local to the |
|||
# current scope. Read only. Thread local. |
|||
alias $LAST_PAREN_MATCH $+ |
|||
@ -0,0 +1,18 @@ |
|||
# Env.rb -- imports environment variables as global variables, Perlish ;( |
|||
# Usage: |
|||
# |
|||
# require 'Env' |
|||
# p $USER |
|||
# $USER = "matz" |
|||
# p ENV["USER"] |
|||
|
|||
require 'importenv' |
|||
|
|||
if __FILE__ == $0 |
|||
p $TERM |
|||
$TERM = nil |
|||
p $TERM |
|||
p ENV["TERM"] |
|||
$TERM = "foo" |
|||
p ENV["TERM"] |
|||
end |
|||
@ -0,0 +1,103 @@ |
|||
#!/usr/bin/env ruby |
|||
=begin |
|||
# |
|||
# Copyright (c) 2001,2003 Akinori MUSHA <knu@iDaemons.org> |
|||
# |
|||
# All rights reserved. You can redistribute and/or modify it under |
|||
# the same terms as Ruby. |
|||
# |
|||
# $Idaemons: /home/cvs/rb/abbrev.rb,v 1.2 2001/05/30 09:37:45 knu Exp $ |
|||
# $RoughId: abbrev.rb,v 1.4 2003/10/14 19:45:42 knu Exp $ |
|||
# $Id: abbrev.rb 11708 2007-02-12 23:01:19Z shyouhei $ |
|||
=end |
|||
|
|||
# Calculate the set of unique abbreviations for a given set of strings. |
|||
# |
|||
# require 'abbrev' |
|||
# require 'pp' |
|||
# |
|||
# pp Abbrev::abbrev(['ruby', 'rules']).sort |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# [["rub", "ruby"], |
|||
# ["ruby", "ruby"], |
|||
# ["rul", "rules"], |
|||
# ["rule", "rules"], |
|||
# ["rules", "rules"]] |
|||
# |
|||
# Also adds an +abbrev+ method to class +Array+. |
|||
|
|||
module Abbrev |
|||
|
|||
# Given a set of strings, calculate the set of unambiguous |
|||
# abbreviations for those strings, and return a hash where the keys |
|||
# are all the possible abbreviations and the values are the full |
|||
# strings. Thus, given input of "car" and "cone", the keys pointing |
|||
# to "car" would be "ca" and "car", while those pointing to "cone" |
|||
# would be "co", "con", and "cone". |
|||
# |
|||
# The optional +pattern+ parameter is a pattern or a string. Only |
|||
# those input strings matching the pattern, or begging the string, |
|||
# are considered for inclusion in the output hash |
|||
|
|||
def abbrev(words, pattern = nil) |
|||
table = {} |
|||
seen = Hash.new(0) |
|||
|
|||
if pattern.is_a?(String) |
|||
pattern = /^#{Regexp.quote(pattern)}/ # regard as a prefix |
|||
end |
|||
|
|||
words.each do |word| |
|||
next if (abbrev = word).empty? |
|||
while (len = abbrev.rindex(/[\w\W]\z/)) > 0 |
|||
abbrev = word[0,len] |
|||
|
|||
next if pattern && pattern !~ abbrev |
|||
|
|||
case seen[abbrev] += 1 |
|||
when 1 |
|||
table[abbrev] = word |
|||
when 2 |
|||
table.delete(abbrev) |
|||
else |
|||
break |
|||
end |
|||
end |
|||
end |
|||
|
|||
words.each do |word| |
|||
next if pattern && pattern !~ word |
|||
|
|||
table[word] = word |
|||
end |
|||
|
|||
table |
|||
end |
|||
|
|||
module_function :abbrev |
|||
end |
|||
|
|||
class Array |
|||
# Calculates the set of unambiguous abbreviations for the strings in |
|||
# +self+. If passed a pattern or a string, only the strings matching |
|||
# the pattern or starting with the string are considered. |
|||
# |
|||
# %w{ car cone }.abbrev #=> { "ca" => "car", "car" => "car", |
|||
# "co" => "cone", "con" => cone", |
|||
# "cone" => "cone" } |
|||
def abbrev(pattern = nil) |
|||
Abbrev::abbrev(self, pattern) |
|||
end |
|||
end |
|||
|
|||
if $0 == __FILE__ |
|||
while line = gets |
|||
hash = line.split.abbrev |
|||
|
|||
hash.sort.each do |k, v| |
|||
puts "#{k} => #{v}" |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,133 @@ |
|||
# |
|||
# = base64.rb: methods for base64-encoding and -decoding stings |
|||
# |
|||
# Author:: Yukihiro Matsumoto |
|||
# Documentation:: Dave Thomas and Gavin Sinclair |
|||
# |
|||
# Until Ruby 1.8.1, these methods were defined at the top-level. Now |
|||
# they are in the Base64 module but included in the top-level, where |
|||
# their usage is deprecated. |
|||
# |
|||
# See Base64 for documentation. |
|||
# |
|||
|
|||
require "kconv" |
|||
|
|||
|
|||
# The Base64 module provides for the encoding (#encode64) and decoding |
|||
# (#decode64) of binary data using a Base64 representation. |
|||
# |
|||
# The following particular features are also provided: |
|||
# - encode into lines of a given length (#b64encode) |
|||
# - decode the special format specified in RFC2047 for the |
|||
# representation of email headers (decode_b) |
|||
# |
|||
# == Example |
|||
# |
|||
# A simple encoding and decoding. |
|||
# |
|||
# require "base64" |
|||
# |
|||
# enc = Base64.encode64('Send reinforcements') |
|||
# # -> "U2VuZCByZWluZm9yY2VtZW50cw==\n" |
|||
# plain = Base64.decode64(enc) |
|||
# # -> "Send reinforcements" |
|||
# |
|||
# The purpose of using base64 to encode data is that it translates any |
|||
# binary data into purely printable characters. It is specified in |
|||
# RFC 2045 (http://www.faqs.org/rfcs/rfc2045.html). |
|||
|
|||
module Base64 |
|||
module_function |
|||
|
|||
# Returns the Base64-decoded version of +str+. |
|||
# |
|||
# require 'base64' |
|||
# str = 'VGhpcyBpcyBsaW5lIG9uZQpUaGlzIG' + |
|||
# 'lzIGxpbmUgdHdvClRoaXMgaXMgbGlu' + |
|||
# 'ZSB0aHJlZQpBbmQgc28gb24uLi4K' |
|||
# puts Base64.decode64(str) |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# This is line one |
|||
# This is line two |
|||
# This is line three |
|||
# And so on... |
|||
|
|||
def decode64(str) |
|||
str.unpack("m")[0] |
|||
end |
|||
|
|||
|
|||
# Decodes text formatted using a subset of RFC2047 (the one used for |
|||
# mime-encoding mail headers). |
|||
# |
|||
# Only supports an encoding type of 'b' (base 64), and only supports |
|||
# the character sets ISO-2022-JP and SHIFT_JIS (so the only two |
|||
# encoded word sequences recognized are <tt>=?ISO-2022-JP?B?...=</tt> and |
|||
# <tt>=?SHIFT_JIS?B?...=</tt>). Recognition of these sequences is case |
|||
# insensitive. |
|||
|
|||
def decode_b(str) |
|||
str.gsub!(/=\?ISO-2022-JP\?B\?([!->@-~]+)\?=/i) { |
|||
decode64($1) |
|||
} |
|||
str = Kconv::toeuc(str) |
|||
str.gsub!(/=\?SHIFT_JIS\?B\?([!->@-~]+)\?=/i) { |
|||
decode64($1) |
|||
} |
|||
str = Kconv::toeuc(str) |
|||
str.gsub!(/\n/, ' ') |
|||
str.gsub!(/\0/, '') |
|||
str |
|||
end |
|||
|
|||
# Returns the Base64-encoded version of +str+. |
|||
# |
|||
# require 'base64' |
|||
# Base64.b64encode("Now is the time for all good coders\nto learn Ruby") |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# Tm93IGlzIHRoZSB0aW1lIGZvciBhbGwgZ29vZCBjb2RlcnMKdG8gbGVhcm4g |
|||
# UnVieQ== |
|||
|
|||
def encode64(bin) |
|||
[bin].pack("m") |
|||
end |
|||
|
|||
# _Prints_ the Base64 encoded version of +bin+ (a +String+) in lines of |
|||
# +len+ (default 60) characters. |
|||
# |
|||
# require 'base64' |
|||
# data = "Now is the time for all good coders\nto learn Ruby" |
|||
# Base64.b64encode(data) |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# Tm93IGlzIHRoZSB0aW1lIGZvciBhbGwgZ29vZCBjb2RlcnMKdG8gbGVhcm4g |
|||
# UnVieQ== |
|||
|
|||
def b64encode(bin, len = 60) |
|||
encode64(bin).scan(/.{1,#{len}}/) do |
|||
print $&, "\n" |
|||
end |
|||
end |
|||
|
|||
|
|||
module Deprecated # :nodoc: |
|||
include Base64 |
|||
|
|||
for m in Base64.private_instance_methods(false) |
|||
module_eval %{ |
|||
def #{m}(*args) |
|||
warn("\#{caller(1)[0]}: #{m} is deprecated; use Base64.#{m} instead") |
|||
super |
|||
end |
|||
} |
|||
end |
|||
end |
|||
end |
|||
|
|||
include Base64::Deprecated |
|||
@ -0,0 +1,572 @@ |
|||
=begin |
|||
# |
|||
# benchmark.rb - a performance benchmarking library |
|||
# |
|||
# $Id: benchmark.rb 17135 2008-06-13 03:10:19Z shyouhei $ |
|||
# |
|||
# Created by Gotoken (gotoken@notwork.org). |
|||
# |
|||
# Documentation by Gotoken (original RD), Lyle Johnson (RDoc conversion), and |
|||
# Gavin Sinclair (editing). |
|||
# |
|||
=end |
|||
|
|||
# == Overview |
|||
# |
|||
# The Benchmark module provides methods for benchmarking Ruby code, giving |
|||
# detailed reports on the time taken for each task. |
|||
# |
|||
|
|||
# The Benchmark module provides methods to measure and report the time |
|||
# used to execute Ruby code. |
|||
# |
|||
# * Measure the time to construct the string given by the expression |
|||
# <tt>"a"*1_000_000</tt>: |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# puts Benchmark.measure { "a"*1_000_000 } |
|||
# |
|||
# On my machine (FreeBSD 3.2 on P5, 100MHz) this generates: |
|||
# |
|||
# 1.166667 0.050000 1.216667 ( 0.571355) |
|||
# |
|||
# This report shows the user CPU time, system CPU time, the sum of |
|||
# the user and system CPU times, and the elapsed real time. The unit |
|||
# of time is seconds. |
|||
# |
|||
# * Do some experiments sequentially using the #bm method: |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# n = 50000 |
|||
# Benchmark.bm do |x| |
|||
# x.report { for i in 1..n; a = "1"; end } |
|||
# x.report { n.times do ; a = "1"; end } |
|||
# x.report { 1.upto(n) do ; a = "1"; end } |
|||
# end |
|||
# |
|||
# The result: |
|||
# |
|||
# user system total real |
|||
# 1.033333 0.016667 1.016667 ( 0.492106) |
|||
# 1.483333 0.000000 1.483333 ( 0.694605) |
|||
# 1.516667 0.000000 1.516667 ( 0.711077) |
|||
# |
|||
# * Continuing the previous example, put a label in each report: |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# n = 50000 |
|||
# Benchmark.bm(7) do |x| |
|||
# x.report("for:") { for i in 1..n; a = "1"; end } |
|||
# x.report("times:") { n.times do ; a = "1"; end } |
|||
# x.report("upto:") { 1.upto(n) do ; a = "1"; end } |
|||
# end |
|||
# |
|||
# The result: |
|||
# |
|||
# user system total real |
|||
# for: 1.050000 0.000000 1.050000 ( 0.503462) |
|||
# times: 1.533333 0.016667 1.550000 ( 0.735473) |
|||
# upto: 1.500000 0.016667 1.516667 ( 0.711239) |
|||
# |
|||
# |
|||
# * The times for some benchmarks depend on the order in which items |
|||
# are run. These differences are due to the cost of memory |
|||
# allocation and garbage collection. To avoid these discrepancies, |
|||
# the #bmbm method is provided. For example, to compare ways to |
|||
# sort an array of floats: |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# array = (1..1000000).map { rand } |
|||
# |
|||
# Benchmark.bmbm do |x| |
|||
# x.report("sort!") { array.dup.sort! } |
|||
# x.report("sort") { array.dup.sort } |
|||
# end |
|||
# |
|||
# The result: |
|||
# |
|||
# Rehearsal ----------------------------------------- |
|||
# sort! 11.928000 0.010000 11.938000 ( 12.756000) |
|||
# sort 13.048000 0.020000 13.068000 ( 13.857000) |
|||
# ------------------------------- total: 25.006000sec |
|||
# |
|||
# user system total real |
|||
# sort! 12.959000 0.010000 12.969000 ( 13.793000) |
|||
# sort 12.007000 0.000000 12.007000 ( 12.791000) |
|||
# |
|||
# |
|||
# * Report statistics of sequential experiments with unique labels, |
|||
# using the #benchmark method: |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# n = 50000 |
|||
# Benchmark.benchmark(" "*7 + CAPTION, 7, FMTSTR, ">total:", ">avg:") do |x| |
|||
# tf = x.report("for:") { for i in 1..n; a = "1"; end } |
|||
# tt = x.report("times:") { n.times do ; a = "1"; end } |
|||
# tu = x.report("upto:") { 1.upto(n) do ; a = "1"; end } |
|||
# [tf+tt+tu, (tf+tt+tu)/3] |
|||
# end |
|||
# |
|||
# The result: |
|||
# |
|||
# user system total real |
|||
# for: 1.016667 0.016667 1.033333 ( 0.485749) |
|||
# times: 1.450000 0.016667 1.466667 ( 0.681367) |
|||
# upto: 1.533333 0.000000 1.533333 ( 0.722166) |
|||
# >total: 4.000000 0.033333 4.033333 ( 1.889282) |
|||
# >avg: 1.333333 0.011111 1.344444 ( 0.629761) |
|||
|
|||
module Benchmark |
|||
|
|||
BENCHMARK_VERSION = "2002-04-25" #:nodoc" |
|||
|
|||
def Benchmark::times() # :nodoc: |
|||
Process::times() |
|||
end |
|||
|
|||
|
|||
# Invokes the block with a <tt>Benchmark::Report</tt> object, which |
|||
# may be used to collect and report on the results of individual |
|||
# benchmark tests. Reserves <i>label_width</i> leading spaces for |
|||
# labels on each line. Prints _caption_ at the top of the |
|||
# report, and uses _fmt_ to format each line. |
|||
# If the block returns an array of |
|||
# <tt>Benchmark::Tms</tt> objects, these will be used to format |
|||
# additional lines of output. If _label_ parameters are |
|||
# given, these are used to label these extra lines. |
|||
# |
|||
# _Note_: Other methods provide a simpler interface to this one, and are |
|||
# suitable for nearly all benchmarking requirements. See the examples in |
|||
# Benchmark, and the #bm and #bmbm methods. |
|||
# |
|||
# Example: |
|||
# |
|||
# require 'benchmark' |
|||
# include Benchmark # we need the CAPTION and FMTSTR constants |
|||
# |
|||
# n = 50000 |
|||
# Benchmark.benchmark(" "*7 + CAPTION, 7, FMTSTR, ">total:", ">avg:") do |x| |
|||
# tf = x.report("for:") { for i in 1..n; a = "1"; end } |
|||
# tt = x.report("times:") { n.times do ; a = "1"; end } |
|||
# tu = x.report("upto:") { 1.upto(n) do ; a = "1"; end } |
|||
# [tf+tt+tu, (tf+tt+tu)/3] |
|||
# end |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# user system total real |
|||
# for: 1.016667 0.016667 1.033333 ( 0.485749) |
|||
# times: 1.450000 0.016667 1.466667 ( 0.681367) |
|||
# upto: 1.533333 0.000000 1.533333 ( 0.722166) |
|||
# >total: 4.000000 0.033333 4.033333 ( 1.889282) |
|||
# >avg: 1.333333 0.011111 1.344444 ( 0.629761) |
|||
# |
|||
|
|||
def benchmark(caption = "", label_width = nil, fmtstr = nil, *labels) # :yield: report |
|||
sync = STDOUT.sync |
|||
STDOUT.sync = true |
|||
label_width ||= 0 |
|||
fmtstr ||= FMTSTR |
|||
raise ArgumentError, "no block" unless iterator? |
|||
print caption |
|||
results = yield(Report.new(label_width, fmtstr)) |
|||
Array === results and results.grep(Tms).each {|t| |
|||
print((labels.shift || t.label || "").ljust(label_width), |
|||
t.format(fmtstr)) |
|||
} |
|||
STDOUT.sync = sync |
|||
end |
|||
|
|||
|
|||
# A simple interface to the #benchmark method, #bm is generates sequential reports |
|||
# with labels. The parameters have the same meaning as for #benchmark. |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# n = 50000 |
|||
# Benchmark.bm(7) do |x| |
|||
# x.report("for:") { for i in 1..n; a = "1"; end } |
|||
# x.report("times:") { n.times do ; a = "1"; end } |
|||
# x.report("upto:") { 1.upto(n) do ; a = "1"; end } |
|||
# end |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# user system total real |
|||
# for: 1.050000 0.000000 1.050000 ( 0.503462) |
|||
# times: 1.533333 0.016667 1.550000 ( 0.735473) |
|||
# upto: 1.500000 0.016667 1.516667 ( 0.711239) |
|||
# |
|||
|
|||
def bm(label_width = 0, *labels, &blk) # :yield: report |
|||
benchmark(" "*label_width + CAPTION, label_width, FMTSTR, *labels, &blk) |
|||
end |
|||
|
|||
|
|||
# Sometimes benchmark results are skewed because code executed |
|||
# earlier encounters different garbage collection overheads than |
|||
# that run later. #bmbm attempts to minimize this effect by running |
|||
# the tests twice, the first time as a rehearsal in order to get the |
|||
# runtime environment stable, the second time for |
|||
# real. <tt>GC.start</tt> is executed before the start of each of |
|||
# the real timings; the cost of this is not included in the |
|||
# timings. In reality, though, there's only so much that #bmbm can |
|||
# do, and the results are not guaranteed to be isolated from garbage |
|||
# collection and other effects. |
|||
# |
|||
# Because #bmbm takes two passes through the tests, it can |
|||
# calculate the required label width. |
|||
# |
|||
# require 'benchmark' |
|||
# |
|||
# array = (1..1000000).map { rand } |
|||
# |
|||
# Benchmark.bmbm do |x| |
|||
# x.report("sort!") { array.dup.sort! } |
|||
# x.report("sort") { array.dup.sort } |
|||
# end |
|||
# |
|||
# <i>Generates:</i> |
|||
# |
|||
# Rehearsal ----------------------------------------- |
|||
# sort! 11.928000 0.010000 11.938000 ( 12.756000) |
|||
# sort 13.048000 0.020000 13.068000 ( 13.857000) |
|||
# ------------------------------- total: 25.006000sec |
|||
# |
|||
# user system total real |
|||
# sort! 12.959000 0.010000 12.969000 ( 13.793000) |
|||
# sort 12.007000 0.000000 12.007000 ( 12.791000) |
|||
# |
|||
# #bmbm yields a Benchmark::Job object and returns an array of |
|||
# Benchmark::Tms objects. |
|||
# |
|||
def bmbm(width = 0, &blk) # :yield: job |
|||
job = Job.new(width) |
|||
yield(job) |
|||
width = job.width |
|||
sync = STDOUT.sync |
|||
STDOUT.sync = true |
|||
|
|||
# rehearsal |
|||
print "Rehearsal " |
|||
puts '-'*(width+CAPTION.length - "Rehearsal ".length) |
|||
list = [] |
|||
job.list.each{|label,item| |
|||
print(label.ljust(width)) |
|||
res = Benchmark::measure(&item) |
|||
print res.format() |
|||
list.push res |
|||
} |
|||
sum = Tms.new; list.each{|i| sum += i} |
|||
ets = sum.format("total: %tsec") |
|||
printf("%s %s\n\n", |
|||
"-"*(width+CAPTION.length-ets.length-1), ets) |
|||
|
|||
# take |
|||
print ' '*width, CAPTION |
|||
list = [] |
|||
ary = [] |
|||
job.list.each{|label,item| |
|||
GC::start |
|||
print label.ljust(width) |
|||
res = Benchmark::measure(&item) |
|||
print res.format() |
|||
ary.push res |
|||
list.push [label, res] |
|||
} |
|||
|
|||
STDOUT.sync = sync |
|||
ary |
|||
end |
|||
|
|||
# |
|||
# Returns the time used to execute the given block as a |
|||
# Benchmark::Tms object. |
|||
# |
|||
def measure(label = "") # :yield: |
|||
t0, r0 = Benchmark.times, Time.now |
|||
yield |
|||
t1, r1 = Benchmark.times, Time.now |
|||
Benchmark::Tms.new(t1.utime - t0.utime, |
|||
t1.stime - t0.stime, |
|||
t1.cutime - t0.cutime, |
|||
t1.cstime - t0.cstime, |
|||
r1.to_f - r0.to_f, |
|||
label) |
|||
end |
|||
|
|||
# |
|||
# Returns the elapsed real time used to execute the given block. |
|||
# |
|||
def realtime(&blk) # :yield: |
|||
r0 = Time.now |
|||
yield |
|||
r1 = Time.now |
|||
r1.to_f - r0.to_f |
|||
end |
|||
|
|||
|
|||
|
|||
# |
|||
# A Job is a sequence of labelled blocks to be processed by the |
|||
# Benchmark.bmbm method. It is of little direct interest to the user. |
|||
# |
|||
class Job # :nodoc: |
|||
# |
|||
# Returns an initialized Job instance. |
|||
# Usually, one doesn't call this method directly, as new |
|||
# Job objects are created by the #bmbm method. |
|||
# _width_ is a initial value for the label offset used in formatting; |
|||
# the #bmbm method passes its _width_ argument to this constructor. |
|||
# |
|||
def initialize(width) |
|||
@width = width |
|||
@list = [] |
|||
end |
|||
|
|||
# |
|||
# Registers the given label and block pair in the job list. |
|||
# |
|||
def item(label = "", &blk) # :yield: |
|||
raise ArgumentError, "no block" unless block_given? |
|||
label.concat ' ' |
|||
w = label.length |
|||
@width = w if @width < w |
|||
@list.push [label, blk] |
|||
self |
|||
end |
|||
|
|||
alias report item |
|||
|
|||
# An array of 2-element arrays, consisting of label and block pairs. |
|||
attr_reader :list |
|||
|
|||
# Length of the widest label in the #list, plus one. |
|||
attr_reader :width |
|||
end |
|||
|
|||
module_function :benchmark, :measure, :realtime, :bm, :bmbm |
|||
|
|||
|
|||
|
|||
# |
|||
# This class is used by the Benchmark.benchmark and Benchmark.bm methods. |
|||
# It is of little direct interest to the user. |
|||
# |
|||
class Report # :nodoc: |
|||
# |
|||
# Returns an initialized Report instance. |
|||
# Usually, one doesn't call this method directly, as new |
|||
# Report objects are created by the #benchmark and #bm methods. |
|||
# _width_ and _fmtstr_ are the label offset and |
|||
# format string used by Tms#format. |
|||
# |
|||
def initialize(width = 0, fmtstr = nil) |
|||
@width, @fmtstr = width, fmtstr |
|||
end |
|||
|
|||
# |
|||
# Prints the _label_ and measured time for the block, |
|||
# formatted by _fmt_. See Tms#format for the |
|||
# formatting rules. |
|||
# |
|||
def item(label = "", *fmt, &blk) # :yield: |
|||
print label.ljust(@width) |
|||
res = Benchmark::measure(&blk) |
|||
print res.format(@fmtstr, *fmt) |
|||
res |
|||
end |
|||
|
|||
alias report item |
|||
end |
|||
|
|||
|
|||
|
|||
# |
|||
# A data object, representing the times associated with a benchmark |
|||
# measurement. |
|||
# |
|||
class Tms |
|||
CAPTION = " user system total real\n" |
|||
FMTSTR = "%10.6u %10.6y %10.6t %10.6r\n" |
|||
|
|||
# User CPU time |
|||
attr_reader :utime |
|||
|
|||
# System CPU time |
|||
attr_reader :stime |
|||
|
|||
# User CPU time of children |
|||
attr_reader :cutime |
|||
|
|||
# System CPU time of children |
|||
attr_reader :cstime |
|||
|
|||
# Elapsed real time |
|||
attr_reader :real |
|||
|
|||
# Total time, that is _utime_ + _stime_ + _cutime_ + _cstime_ |
|||
attr_reader :total |
|||
|
|||
# Label |
|||
attr_reader :label |
|||
|
|||
# |
|||
# Returns an initialized Tms object which has |
|||
# _u_ as the user CPU time, _s_ as the system CPU time, |
|||
# _cu_ as the children's user CPU time, _cs_ as the children's |
|||
# system CPU time, _real_ as the elapsed real time and _l_ |
|||
# as the label. |
|||
# |
|||
def initialize(u = 0.0, s = 0.0, cu = 0.0, cs = 0.0, real = 0.0, l = nil) |
|||
@utime, @stime, @cutime, @cstime, @real, @label = u, s, cu, cs, real, l |
|||
@total = @utime + @stime + @cutime + @cstime |
|||
end |
|||
|
|||
# |
|||
# Returns a new Tms object whose times are the sum of the times for this |
|||
# Tms object, plus the time required to execute the code block (_blk_). |
|||
# |
|||
def add(&blk) # :yield: |
|||
self + Benchmark::measure(&blk) |
|||
end |
|||
|
|||
# |
|||
# An in-place version of #add. |
|||
# |
|||
def add! |
|||
t = Benchmark::measure(&blk) |
|||
@utime = utime + t.utime |
|||
@stime = stime + t.stime |
|||
@cutime = cutime + t.cutime |
|||
@cstime = cstime + t.cstime |
|||
@real = real + t.real |
|||
self |
|||
end |
|||
|
|||
# |
|||
# Returns a new Tms object obtained by memberwise summation |
|||
# of the individual times for this Tms object with those of the other |
|||
# Tms object. |
|||
# This method and #/() are useful for taking statistics. |
|||
# |
|||
def +(other); memberwise(:+, other) end |
|||
|
|||
# |
|||
# Returns a new Tms object obtained by memberwise subtraction |
|||
# of the individual times for the other Tms object from those of this |
|||
# Tms object. |
|||
# |
|||
def -(other); memberwise(:-, other) end |
|||
|
|||
# |
|||
# Returns a new Tms object obtained by memberwise multiplication |
|||
# of the individual times for this Tms object by _x_. |
|||
# |
|||
def *(x); memberwise(:*, x) end |
|||
|
|||
# |
|||
# Returns a new Tms object obtained by memberwise division |
|||
# of the individual times for this Tms object by _x_. |
|||
# This method and #+() are useful for taking statistics. |
|||
# |
|||
def /(x); memberwise(:/, x) end |
|||
|
|||
# |
|||
# Returns the contents of this Tms object as |
|||
# a formatted string, according to a format string |
|||
# like that passed to Kernel.format. In addition, #format |
|||
# accepts the following extensions: |
|||
# |
|||
# <tt>%u</tt>:: Replaced by the user CPU time, as reported by Tms#utime. |
|||
# <tt>%y</tt>:: Replaced by the system CPU time, as reported by #stime (Mnemonic: y of "s*y*stem") |
|||
# <tt>%U</tt>:: Replaced by the children's user CPU time, as reported by Tms#cutime |
|||
# <tt>%Y</tt>:: Replaced by the children's system CPU time, as reported by Tms#cstime |
|||
# <tt>%t</tt>:: Replaced by the total CPU time, as reported by Tms#total |
|||
# <tt>%r</tt>:: Replaced by the elapsed real time, as reported by Tms#real |
|||
# <tt>%n</tt>:: Replaced by the label string, as reported by Tms#label (Mnemonic: n of "*n*ame") |
|||
# |
|||
# If _fmtstr_ is not given, FMTSTR is used as default value, detailing the |
|||
# user, system and real elapsed time. |
|||
# |
|||
def format(arg0 = nil, *args) |
|||
fmtstr = (arg0 || FMTSTR).dup |
|||
fmtstr.gsub!(/(%[-+\.\d]*)n/){"#{$1}s" % label} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)u/){"#{$1}f" % utime} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)y/){"#{$1}f" % stime} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)U/){"#{$1}f" % cutime} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)Y/){"#{$1}f" % cstime} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)t/){"#{$1}f" % total} |
|||
fmtstr.gsub!(/(%[-+\.\d]*)r/){"(#{$1}f)" % real} |
|||
arg0 ? Kernel::format(fmtstr, *args) : fmtstr |
|||
end |
|||
|
|||
# |
|||
# Same as #format. |
|||
# |
|||
def to_s |
|||
format |
|||
end |
|||
|
|||
# |
|||
# Returns a new 6-element array, consisting of the |
|||
# label, user CPU time, system CPU time, children's |
|||
# user CPU time, children's system CPU time and elapsed |
|||
# real time. |
|||
# |
|||
def to_a |
|||
[@label, @utime, @stime, @cutime, @cstime, @real] |
|||
end |
|||
|
|||
protected |
|||
def memberwise(op, x) |
|||
case x |
|||
when Benchmark::Tms |
|||
Benchmark::Tms.new(utime.__send__(op, x.utime), |
|||
stime.__send__(op, x.stime), |
|||
cutime.__send__(op, x.cutime), |
|||
cstime.__send__(op, x.cstime), |
|||
real.__send__(op, x.real) |
|||
) |
|||
else |
|||
Benchmark::Tms.new(utime.__send__(op, x), |
|||
stime.__send__(op, x), |
|||
cutime.__send__(op, x), |
|||
cstime.__send__(op, x), |
|||
real.__send__(op, x) |
|||
) |
|||
end |
|||
end |
|||
end |
|||
|
|||
# The default caption string (heading above the output times). |
|||
CAPTION = Benchmark::Tms::CAPTION |
|||
|
|||
# The default format string used to display times. See also Benchmark::Tms#format. |
|||
FMTSTR = Benchmark::Tms::FMTSTR |
|||
end |
|||
|
|||
if __FILE__ == $0 |
|||
include Benchmark |
|||
|
|||
n = ARGV[0].to_i.nonzero? || 50000 |
|||
puts %Q([#{n} times iterations of `a = "1"']) |
|||
benchmark(" " + CAPTION, 7, FMTSTR) do |x| |
|||
x.report("for:") {for i in 1..n; a = "1"; end} # Benchmark::measure |
|||
x.report("times:") {n.times do ; a = "1"; end} |
|||
x.report("upto:") {1.upto(n) do ; a = "1"; end} |
|||
end |
|||
|
|||
benchmark do |
|||
[ |
|||
measure{for i in 1..n; a = "1"; end}, # Benchmark::measure |
|||
measure{n.times do ; a = "1"; end}, |
|||
measure{1.upto(n) do ; a = "1"; end} |
|||
] |
|||
end |
|||
end |
|||
@ -0,0 +1,85 @@ |
|||
# |
|||
# require 'bigdecimal/jacobian' |
|||
# |
|||
# Provides methods to compute the Jacobian matrix of a set of equations at a |
|||
# point x. In the methods below: |
|||
# |
|||
# f is an Object which is used to compute the Jacobian matrix of the equations. |
|||
# It must provide the following methods: |
|||
# |
|||
# f.values(x):: returns the values of all functions at x |
|||
# |
|||
# f.zero:: returns 0.0 |
|||
# f.one:: returns 1.0 |
|||
# f.two:: returns 1.0 |
|||
# f.ten:: returns 10.0 |
|||
# |
|||
# f.eps:: returns the convergence criterion (epsilon value) used to determine whether two values are considered equal. If |a-b| < epsilon, the two values are considered equal. |
|||
# |
|||
# x is the point at which to compute the Jacobian. |
|||
# |
|||
# fx is f.values(x). |
|||
# |
|||
module Jacobian |
|||
#-- |
|||
def isEqual(a,b,zero=0.0,e=1.0e-8) |
|||
aa = a.abs |
|||
bb = b.abs |
|||
if aa == zero && bb == zero then |
|||
true |
|||
else |
|||
if ((a-b)/(aa+bb)).abs < e then |
|||
true |
|||
else |
|||
false |
|||
end |
|||
end |
|||
end |
|||
#++ |
|||
|
|||
# Computes the derivative of f[i] at x[i]. |
|||
# fx is the value of f at x. |
|||
def dfdxi(f,fx,x,i) |
|||
nRetry = 0 |
|||
n = x.size |
|||
xSave = x[i] |
|||
ok = 0 |
|||
ratio = f.ten*f.ten*f.ten |
|||
dx = x[i].abs/ratio |
|||
dx = fx[i].abs/ratio if isEqual(dx,f.zero,f.zero,f.eps) |
|||
dx = f.one/f.ten if isEqual(dx,f.zero,f.zero,f.eps) |
|||
until ok>0 do |
|||
s = f.zero |
|||
deriv = [] |
|||
if(nRetry>100) then |
|||
raize "Singular Jacobian matrix. No change at x[" + i.to_s + "]" |
|||
end |
|||
dx = dx*f.two |
|||
x[i] += dx |
|||
fxNew = f.values(x) |
|||
for j in 0...n do |
|||
if !isEqual(fxNew[j],fx[j],f.zero,f.eps) then |
|||
ok += 1 |
|||
deriv <<= (fxNew[j]-fx[j])/dx |
|||
else |
|||
deriv <<= f.zero |
|||
end |
|||
end |
|||
x[i] = xSave |
|||
end |
|||
deriv |
|||
end |
|||
|
|||
# Computes the Jacobian of f at x. fx is the value of f at x. |
|||
def jacobian(f,fx,x) |
|||
n = x.size |
|||
dfdx = Array::new(n*n) |
|||
for i in 0...n do |
|||
df = dfdxi(f,fx,x,i) |
|||
for j in 0...n do |
|||
dfdx[j*n+i] = df[j] |
|||
end |
|||
end |
|||
dfdx |
|||
end |
|||
end |
|||
@ -0,0 +1,84 @@ |
|||
# |
|||
# Solves a*x = b for x, using LU decomposition. |
|||
# |
|||
module LUSolve |
|||
# Performs LU decomposition of the n by n matrix a. |
|||
def ludecomp(a,n,zero=0,one=1) |
|||
prec = BigDecimal.limit(nil) |
|||
ps = [] |
|||
scales = [] |
|||
for i in 0...n do # pick up largest(abs. val.) element in each row. |
|||
ps <<= i |
|||
nrmrow = zero |
|||
ixn = i*n |
|||
for j in 0...n do |
|||
biggst = a[ixn+j].abs |
|||
nrmrow = biggst if biggst>nrmrow |
|||
end |
|||
if nrmrow>zero then |
|||
scales <<= one.div(nrmrow,prec) |
|||
else |
|||
raise "Singular matrix" |
|||
end |
|||
end |
|||
n1 = n - 1 |
|||
for k in 0...n1 do # Gaussian elimination with partial pivoting. |
|||
biggst = zero; |
|||
for i in k...n do |
|||
size = a[ps[i]*n+k].abs*scales[ps[i]] |
|||
if size>biggst then |
|||
biggst = size |
|||
pividx = i |
|||
end |
|||
end |
|||
raise "Singular matrix" if biggst<=zero |
|||
if pividx!=k then |
|||
j = ps[k] |
|||
ps[k] = ps[pividx] |
|||
ps[pividx] = j |
|||
end |
|||
pivot = a[ps[k]*n+k] |
|||
for i in (k+1)...n do |
|||
psin = ps[i]*n |
|||
a[psin+k] = mult = a[psin+k].div(pivot,prec) |
|||
if mult!=zero then |
|||
pskn = ps[k]*n |
|||
for j in (k+1)...n do |
|||
a[psin+j] -= mult.mult(a[pskn+j],prec) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
raise "Singular matrix" if a[ps[n1]*n+n1] == zero |
|||
ps |
|||
end |
|||
|
|||
# Solves a*x = b for x, using LU decomposition. |
|||
# |
|||
# a is a matrix, b is a constant vector, x is the solution vector. |
|||
# |
|||
# ps is the pivot, a vector which indicates the permutation of rows performed |
|||
# during LU decomposition. |
|||
def lusolve(a,b,ps,zero=0.0) |
|||
prec = BigDecimal.limit(nil) |
|||
n = ps.size |
|||
x = [] |
|||
for i in 0...n do |
|||
dot = zero |
|||
psin = ps[i]*n |
|||
for j in 0...i do |
|||
dot = a[psin+j].mult(x[j],prec) + dot |
|||
end |
|||
x <<= b[ps[i]] - dot |
|||
end |
|||
(n-1).downto(0) do |i| |
|||
dot = zero |
|||
psin = ps[i]*n |
|||
for j in (i+1)...n do |
|||
dot = a[psin+j].mult(x[j],prec) + dot |
|||
end |
|||
x[i] = (x[i]-dot).div(a[psin+i],prec) |
|||
end |
|||
x |
|||
end |
|||
end |
|||
@ -0,0 +1,235 @@ |
|||
# |
|||
#-- |
|||
# Contents: |
|||
# sqrt(x, prec) |
|||
# sin (x, prec) |
|||
# cos (x, prec) |
|||
# atan(x, prec) Note: |x|<1, x=0.9999 may not converge. |
|||
# exp (x, prec) |
|||
# log (x, prec) |
|||
# PI (prec) |
|||
# E (prec) == exp(1.0,prec) |
|||
# |
|||
# where: |
|||
# x ... BigDecimal number to be computed. |
|||
# |x| must be small enough to get convergence. |
|||
# prec ... Number of digits to be obtained. |
|||
#++ |
|||
# |
|||
# Provides mathematical functions. |
|||
# |
|||
# Example: |
|||
# |
|||
# require "bigdecimal" |
|||
# require "bigdecimal/math" |
|||
# |
|||
# include BigMath |
|||
# |
|||
# a = BigDecimal((PI(100)/2).to_s) |
|||
# puts sin(a,100) # -> 0.10000000000000000000......E1 |
|||
# |
|||
module BigMath |
|||
|
|||
# Computes the square root of x to the specified number of digits of |
|||
# precision. |
|||
# |
|||
# BigDecimal.new('2').sqrt(16).to_s |
|||
# -> "0.14142135623730950488016887242096975E1" |
|||
# |
|||
def sqrt(x,prec) |
|||
x.sqrt(prec) |
|||
end |
|||
|
|||
# Computes the sine of x to the specified number of digits of precision. |
|||
# |
|||
# If x is infinite or NaN, returns NaN. |
|||
def sin(x, prec) |
|||
raise ArgumentError, "Zero or negative precision for sin" if prec <= 0 |
|||
return BigDecimal("NaN") if x.infinite? || x.nan? |
|||
n = prec + BigDecimal.double_fig |
|||
one = BigDecimal("1") |
|||
two = BigDecimal("2") |
|||
x1 = x |
|||
x2 = x.mult(x,n) |
|||
sign = 1 |
|||
y = x |
|||
d = y |
|||
i = one |
|||
z = one |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
sign = -sign |
|||
x1 = x2.mult(x1,n) |
|||
i += two |
|||
z *= (i-one) * i |
|||
d = sign * x1.div(z,m) |
|||
y += d |
|||
end |
|||
y |
|||
end |
|||
|
|||
# Computes the cosine of x to the specified number of digits of precision. |
|||
# |
|||
# If x is infinite or NaN, returns NaN. |
|||
def cos(x, prec) |
|||
raise ArgumentError, "Zero or negative precision for cos" if prec <= 0 |
|||
return BigDecimal("NaN") if x.infinite? || x.nan? |
|||
n = prec + BigDecimal.double_fig |
|||
one = BigDecimal("1") |
|||
two = BigDecimal("2") |
|||
x1 = one |
|||
x2 = x.mult(x,n) |
|||
sign = 1 |
|||
y = one |
|||
d = y |
|||
i = BigDecimal("0") |
|||
z = one |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
sign = -sign |
|||
x1 = x2.mult(x1,n) |
|||
i += two |
|||
z *= (i-one) * i |
|||
d = sign * x1.div(z,m) |
|||
y += d |
|||
end |
|||
y |
|||
end |
|||
|
|||
# Computes the arctangent of x to the specified number of digits of precision. |
|||
# |
|||
# If x is infinite or NaN, returns NaN. |
|||
# Raises an argument error if x > 1. |
|||
def atan(x, prec) |
|||
raise ArgumentError, "Zero or negative precision for atan" if prec <= 0 |
|||
return BigDecimal("NaN") if x.infinite? || x.nan? |
|||
raise ArgumentError, "x.abs must be less than 1.0" if x.abs>=1 |
|||
n = prec + BigDecimal.double_fig |
|||
y = x |
|||
d = y |
|||
t = x |
|||
r = BigDecimal("3") |
|||
x2 = x.mult(x,n) |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
t = -t.mult(x2,n) |
|||
d = t.div(r,m) |
|||
y += d |
|||
r += 2 |
|||
end |
|||
y |
|||
end |
|||
|
|||
# Computes the value of e (the base of natural logarithms) raised to the |
|||
# power of x, to the specified number of digits of precision. |
|||
# |
|||
# If x is infinite or NaN, returns NaN. |
|||
# |
|||
# BigMath::exp(BigDecimal.new('1'), 10).to_s |
|||
# -> "0.271828182845904523536028752390026306410273E1" |
|||
def exp(x, prec) |
|||
raise ArgumentError, "Zero or negative precision for exp" if prec <= 0 |
|||
return BigDecimal("NaN") if x.infinite? || x.nan? |
|||
n = prec + BigDecimal.double_fig |
|||
one = BigDecimal("1") |
|||
x1 = one |
|||
y = one |
|||
d = y |
|||
z = one |
|||
i = 0 |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
x1 = x1.mult(x,n) |
|||
i += 1 |
|||
z *= i |
|||
d = x1.div(z,m) |
|||
y += d |
|||
end |
|||
y |
|||
end |
|||
|
|||
# Computes the natural logarithm of x to the specified number of digits |
|||
# of precision. |
|||
# |
|||
# Returns x if x is infinite or NaN. |
|||
# |
|||
def log(x, prec) |
|||
raise ArgumentError, "Zero or negative argument for log" if x <= 0 || prec <= 0 |
|||
return x if x.infinite? || x.nan? |
|||
one = BigDecimal("1") |
|||
two = BigDecimal("2") |
|||
n = prec + BigDecimal.double_fig |
|||
x = (x - one).div(x + one,n) |
|||
x2 = x.mult(x,n) |
|||
y = x |
|||
d = y |
|||
i = one |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
x = x2.mult(x,n) |
|||
i += two |
|||
d = x.div(i,m) |
|||
y += d |
|||
end |
|||
y*two |
|||
end |
|||
|
|||
# Computes the value of pi to the specified number of digits of precision. |
|||
def PI(prec) |
|||
raise ArgumentError, "Zero or negative argument for PI" if prec <= 0 |
|||
n = prec + BigDecimal.double_fig |
|||
zero = BigDecimal("0") |
|||
one = BigDecimal("1") |
|||
two = BigDecimal("2") |
|||
|
|||
m25 = BigDecimal("-0.04") |
|||
m57121 = BigDecimal("-57121") |
|||
|
|||
pi = zero |
|||
|
|||
d = one |
|||
k = one |
|||
w = one |
|||
t = BigDecimal("-80") |
|||
while d.nonzero? && ((m = n - (pi.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
t = t*m25 |
|||
d = t.div(k,m) |
|||
k = k+two |
|||
pi = pi + d |
|||
end |
|||
|
|||
d = one |
|||
k = one |
|||
w = one |
|||
t = BigDecimal("956") |
|||
while d.nonzero? && ((m = n - (pi.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
t = t.div(m57121,n) |
|||
d = t.div(k,m) |
|||
pi = pi + d |
|||
k = k+two |
|||
end |
|||
pi |
|||
end |
|||
|
|||
# Computes e (the base of natural logarithms) to the specified number of |
|||
# digits of precision. |
|||
def E(prec) |
|||
raise ArgumentError, "Zero or negative precision for E" if prec <= 0 |
|||
n = prec + BigDecimal.double_fig |
|||
one = BigDecimal("1") |
|||
y = one |
|||
d = y |
|||
z = one |
|||
i = 0 |
|||
while d.nonzero? && ((m = n - (y.exponent - d.exponent).abs) > 0) |
|||
m = BigDecimal.double_fig if m < BigDecimal.double_fig |
|||
i += 1 |
|||
z *= i |
|||
d = one.div(z,m) |
|||
y += d |
|||
end |
|||
y |
|||
end |
|||
end |
|||
@ -0,0 +1,77 @@ |
|||
# |
|||
# newton.rb |
|||
# |
|||
# Solves the nonlinear algebraic equation system f = 0 by Newton's method. |
|||
# This program is not dependent on BigDecimal. |
|||
# |
|||
# To call: |
|||
# n = nlsolve(f,x) |
|||
# where n is the number of iterations required, |
|||
# x is the initial value vector |
|||
# f is an Object which is used to compute the values of the equations to be solved. |
|||
# It must provide the following methods: |
|||
# |
|||
# f.values(x):: returns the values of all functions at x |
|||
# |
|||
# f.zero:: returns 0.0 |
|||
# f.one:: returns 1.0 |
|||
# f.two:: returns 1.0 |
|||
# f.ten:: returns 10.0 |
|||
# |
|||
# f.eps:: returns the convergence criterion (epsilon value) used to determine whether two values are considered equal. If |a-b| < epsilon, the two values are considered equal. |
|||
# |
|||
# On exit, x is the solution vector. |
|||
# |
|||
require "bigdecimal/ludcmp" |
|||
require "bigdecimal/jacobian" |
|||
|
|||
module Newton |
|||
include LUSolve |
|||
include Jacobian |
|||
|
|||
def norm(fv,zero=0.0) |
|||
s = zero |
|||
n = fv.size |
|||
for i in 0...n do |
|||
s += fv[i]*fv[i] |
|||
end |
|||
s |
|||
end |
|||
|
|||
def nlsolve(f,x) |
|||
nRetry = 0 |
|||
n = x.size |
|||
|
|||
f0 = f.values(x) |
|||
zero = f.zero |
|||
one = f.one |
|||
two = f.two |
|||
p5 = one/two |
|||
d = norm(f0,zero) |
|||
minfact = f.ten*f.ten*f.ten |
|||
minfact = one/minfact |
|||
e = f.eps |
|||
while d >= e do |
|||
nRetry += 1 |
|||
# Not yet converged. => Compute Jacobian matrix |
|||
dfdx = jacobian(f,f0,x) |
|||
# Solve dfdx*dx = -f0 to estimate dx |
|||
dx = lusolve(dfdx,f0,ludecomp(dfdx,n,zero,one),zero) |
|||
fact = two |
|||
xs = x.dup |
|||
begin |
|||
fact *= p5 |
|||
if fact < minfact then |
|||
raise "Failed to reduce function values." |
|||
end |
|||
for i in 0...n do |
|||
x[i] = xs[i] - dx[i]*fact |
|||
end |
|||
f0 = f.values(x) |
|||
dn = norm(f0,zero) |
|||
end while(dn>=d) |
|||
d = dn |
|||
end |
|||
nRetry |
|||
end |
|||
end |
|||
@ -0,0 +1,65 @@ |
|||
# |
|||
# BigDecimal utility library. |
|||
# |
|||
# To use these functions, require 'bigdecimal/util' |
|||
# |
|||
# The following methods are provided to convert other types to BigDecimals: |
|||
# |
|||
# String#to_d -> BigDecimal |
|||
# Float#to_d -> BigDecimal |
|||
# Rational#to_d -> BigDecimal |
|||
# |
|||
# The following method is provided to convert BigDecimals to other types: |
|||
# |
|||
# BigDecimal#to_r -> Rational |
|||
# |
|||
# ---------------------------------------------------------------------- |
|||
# |
|||
class Float < Numeric |
|||
def to_d |
|||
BigDecimal(self.to_s) |
|||
end |
|||
end |
|||
|
|||
class String |
|||
def to_d |
|||
BigDecimal(self) |
|||
end |
|||
end |
|||
|
|||
class BigDecimal < Numeric |
|||
# Converts a BigDecimal to a String of the form "nnnnnn.mmm". |
|||
# This method is deprecated; use BigDecimal#to_s("F") instead. |
|||
def to_digits |
|||
if self.nan? || self.infinite? || self.zero? |
|||
self.to_s |
|||
else |
|||
i = self.to_i.to_s |
|||
s,f,y,z = self.frac.split |
|||
i + "." + ("0"*(-z)) + f |
|||
end |
|||
end |
|||
|
|||
# Converts a BigDecimal to a Rational. |
|||
def to_r |
|||
sign,digits,base,power = self.split |
|||
numerator = sign*digits.to_i |
|||
denomi_power = power - digits.size # base is always 10 |
|||
if denomi_power < 0 |
|||
Rational(numerator,base ** (-denomi_power)) |
|||
else |
|||
Rational(numerator * (base ** denomi_power),1) |
|||
end |
|||
end |
|||
end |
|||
|
|||
class Rational < Numeric |
|||
# Converts a Rational to a BigDecimal |
|||
def to_d(nFig=0) |
|||
num = self.numerator.to_s |
|||
if nFig<=0 |
|||
nFig = BigDecimal.double_fig*2+1 |
|||
end |
|||
BigDecimal.new(num).div(self.denominator,nFig) |
|||
end |
|||
end |
|||
@ -0,0 +1,272 @@ |
|||
warn "Warning:#{caller[0].sub(/:in `.*'\z/, '')}: cgi-lib is deprecated after Ruby 1.8.1; use cgi instead" |
|||
|
|||
=begin |
|||
|
|||
= simple CGI support library |
|||
|
|||
= example |
|||
|
|||
== get form values |
|||
|
|||
require "cgi-lib.rb" |
|||
query = CGI.new |
|||
query['field'] # <== value of 'field' |
|||
query.keys # <== array of fields |
|||
|
|||
and query has Hash class methods |
|||
|
|||
|
|||
== get cookie values |
|||
|
|||
require "cgi-lib.rb" |
|||
query = CGI.new |
|||
query.cookie['name'] # <== cookie value of 'name' |
|||
query.cookie.keys # <== all cookie names |
|||
|
|||
and query.cookie has Hash class methods |
|||
|
|||
|
|||
== print HTTP header and HTML string to $> |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::print{ |
|||
CGI::tag("HTML"){ |
|||
CGI::tag("HEAD"){ CGI::tag("TITLE"){"TITLE"} } + |
|||
CGI::tag("BODY"){ |
|||
CGI::tag("FORM", {"ACTION"=>"test.rb", "METHOD"=>"POST"}){ |
|||
CGI::tag("INPUT", {"TYPE"=>"submit", "VALUE"=>"submit"}) |
|||
} + |
|||
CGI::tag("HR") |
|||
} |
|||
} |
|||
} |
|||
|
|||
|
|||
== make raw cookie string |
|||
|
|||
require "cgi-lib.rb" |
|||
cookie1 = CGI::cookie({'name' => 'name', |
|||
'value' => 'value', |
|||
'path' => 'path', # optional |
|||
'domain' => 'domain', # optional |
|||
'expires' => Time.now, # optional |
|||
'secure' => true # optional |
|||
}) |
|||
|
|||
CGI::print("Content-Type: text/html", cookie1, cookie2){ "string" } |
|||
|
|||
|
|||
== print HTTP header and string to $> |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::print{ "string" } |
|||
# == CGI::print("Content-Type: text/html"){ "string" } |
|||
CGI::print("Content-Type: text/html", cookie1, cookie2){ "string" } |
|||
|
|||
|
|||
=== NPH (no-parse-header) mode |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::print("nph"){ "string" } |
|||
# == CGI::print("nph", "Content-Type: text/html"){ "string" } |
|||
CGI::print("nph", "Content-Type: text/html", cookie1, cookie2){ "string" } |
|||
|
|||
|
|||
== make HTML tag string |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::tag("element", {"attribute_name"=>"attribute_value"}){"content"} |
|||
|
|||
|
|||
== make HTTP header string |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::header # == CGI::header("Content-Type: text/html") |
|||
CGI::header("Content-Type: text/html", cookie1, cookie2) |
|||
|
|||
|
|||
=== NPH (no-parse-header) mode |
|||
|
|||
CGI::header("nph") # == CGI::header("nph", "Content-Type: text/html") |
|||
CGI::header("nph", "Content-Type: text/html", cookie1, cookie2) |
|||
|
|||
|
|||
== escape url encode |
|||
|
|||
require "cgi-lib.rb" |
|||
url_encoded_string = CGI::escape("string") |
|||
|
|||
|
|||
== unescape url encoded |
|||
|
|||
require "cgi-lib.rb" |
|||
string = CGI::unescape("url encoded string") |
|||
|
|||
|
|||
== escape HTML &"<> |
|||
|
|||
require "cgi-lib.rb" |
|||
CGI::escapeHTML("string") |
|||
|
|||
|
|||
=end |
|||
|
|||
require "delegate" |
|||
|
|||
class CGI < SimpleDelegator |
|||
|
|||
CR = "\015" |
|||
LF = "\012" |
|||
EOL = CR + LF |
|||
|
|||
RFC822_DAYS = %w[ Sun Mon Tue Wed Thu Fri Sat ] |
|||
RFC822_MONTHS = %w[ Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec ] |
|||
|
|||
# make rfc1123 date string |
|||
def CGI::rfc1123_date(time) |
|||
t = time.clone.gmtime |
|||
return format("%s, %.2d %s %d %.2d:%.2d:%.2d GMT", |
|||
RFC822_DAYS[t.wday], t.day, RFC822_MONTHS[t.month-1], t.year, |
|||
t.hour, t.min, t.sec) |
|||
end |
|||
|
|||
# escape url encode |
|||
def CGI::escape(str) |
|||
str.gsub(/[^a-zA-Z0-9_\-.]/n){ sprintf("%%%02X", $&.unpack("C")[0]) } |
|||
end |
|||
|
|||
# unescape url encoded |
|||
def CGI::unescape(str) |
|||
str.gsub(/\+/, ' ').gsub(/%([0-9a-fA-F]{2})/){ [$1.hex].pack("c") } |
|||
end |
|||
|
|||
# escape HTML |
|||
def CGI::escapeHTML(str) |
|||
str.gsub(/&/, "&").gsub(/\"/, """).gsub(/>/, ">").gsub(/</, "<") |
|||
end |
|||
|
|||
# offline mode. read name=value pairs on standard input. |
|||
def read_from_cmdline |
|||
require "shellwords.rb" |
|||
words = Shellwords.shellwords( |
|||
if not ARGV.empty? |
|||
ARGV.join(' ') |
|||
else |
|||
STDERR.print "(offline mode: enter name=value pairs on standard input)\n" if STDIN.tty? |
|||
readlines.join(' ').gsub(/\n/, '') |
|||
end.gsub(/\\=/, '%3D').gsub(/\\&/, '%26')) |
|||
|
|||
if words.find{|x| x =~ /=/} then words.join('&') else words.join('+') end |
|||
end |
|||
|
|||
def initialize(input = $stdin) |
|||
|
|||
@inputs = {} |
|||
@cookie = {} |
|||
|
|||
case ENV['REQUEST_METHOD'] |
|||
when "GET" |
|||
ENV['QUERY_STRING'] or "" |
|||
when "POST" |
|||
input.read(Integer(ENV['CONTENT_LENGTH'])) or "" |
|||
else |
|||
read_from_cmdline |
|||
end.split(/[&;]/).each do |x| |
|||
key, val = x.split(/=/,2).collect{|x|CGI::unescape(x)} |
|||
if @inputs.include?(key) |
|||
@inputs[key] += "\0" + (val or "") |
|||
else |
|||
@inputs[key] = (val or "") |
|||
end |
|||
end |
|||
|
|||
super(@inputs) |
|||
|
|||
if ENV.has_key?('HTTP_COOKIE') or ENV.has_key?('COOKIE') |
|||
(ENV['HTTP_COOKIE'] or ENV['COOKIE']).split(/; /).each do |x| |
|||
key, val = x.split(/=/,2) |
|||
key = CGI::unescape(key) |
|||
val = val.split(/&/).collect{|x|CGI::unescape(x)}.join("\0") |
|||
if @cookie.include?(key) |
|||
@cookie[key] += "\0" + val |
|||
else |
|||
@cookie[key] = val |
|||
end |
|||
end |
|||
end |
|||
end |
|||
|
|||
attr("inputs") |
|||
attr("cookie") |
|||
|
|||
# make HTML tag string |
|||
def CGI::tag(element, attributes = {}) |
|||
"<" + escapeHTML(element) + attributes.collect{|name, value| |
|||
" " + escapeHTML(name) + '="' + escapeHTML(value) + '"' |
|||
}.to_s + ">" + |
|||
(iterator? ? yield.to_s + "</" + escapeHTML(element) + ">" : "") |
|||
end |
|||
|
|||
# make raw cookie string |
|||
def CGI::cookie(options) |
|||
"Set-Cookie: " + options['name'] + '=' + escape(options['value']) + |
|||
(options['domain'] ? '; domain=' + options['domain'] : '') + |
|||
(options['path'] ? '; path=' + options['path'] : '') + |
|||
(options['expires'] ? '; expires=' + rfc1123_date(options['expires']) : '') + |
|||
(options['secure'] ? '; secure' : '') |
|||
end |
|||
|
|||
# make HTTP header string |
|||
def CGI::header(*options) |
|||
if defined?(MOD_RUBY) |
|||
options.each{|option| |
|||
option.sub(/(.*?): (.*)/){ |
|||
Apache::request.headers_out[$1] = $2 |
|||
} |
|||
} |
|||
Apache::request.send_http_header |
|||
'' |
|||
else |
|||
if options.delete("nph") or (ENV['SERVER_SOFTWARE'] =~ /IIS/) |
|||
[(ENV['SERVER_PROTOCOL'] or "HTTP/1.0") + " 200 OK", |
|||
"Date: " + rfc1123_date(Time.now), |
|||
"Server: " + (ENV['SERVER_SOFTWARE'] or ""), |
|||
"Connection: close"] + |
|||
(options.empty? ? ["Content-Type: text/html"] : options) |
|||
else |
|||
options.empty? ? ["Content-Type: text/html"] : options |
|||
end.join(EOL) + EOL + EOL |
|||
end |
|||
end |
|||
|
|||
# print HTTP header and string to $> |
|||
def CGI::print(*options) |
|||
$>.print CGI::header(*options) + yield.to_s |
|||
end |
|||
|
|||
# print message to $> |
|||
def CGI::message(message, title = "", header = ["Content-Type: text/html"]) |
|||
if message.kind_of?(Hash) |
|||
title = message['title'] |
|||
header = message['header'] |
|||
message = message['body'] |
|||
end |
|||
CGI::print(*header){ |
|||
CGI::tag("HTML"){ |
|||
CGI::tag("HEAD"){ CGI.tag("TITLE"){ title } } + |
|||
CGI::tag("BODY"){ message } |
|||
} |
|||
} |
|||
true |
|||
end |
|||
|
|||
# print error message to $> and exit |
|||
def CGI::error |
|||
CGI::message({'title'=>'ERROR', 'body'=> |
|||
CGI::tag("PRE"){ |
|||
"ERROR: " + CGI::tag("STRONG"){ escapeHTML($!.to_s) } + "\n" + escapeHTML($@.join("\n")) |
|||
} |
|||
}) |
|||
exit |
|||
end |
|||
end |
|||
File diff suppressed because it is too large
@ -0,0 +1,492 @@ |
|||
# |
|||
# cgi/session.rb - session support for cgi scripts |
|||
# |
|||
# Copyright (C) 2001 Yukihiro "Matz" Matsumoto |
|||
# Copyright (C) 2000 Network Applied Communication Laboratory, Inc. |
|||
# Copyright (C) 2000 Information-technology Promotion Agency, Japan |
|||
# |
|||
# Author: Yukihiro "Matz" Matsumoto |
|||
# |
|||
# Documentation: William Webber (william@williamwebber.com) |
|||
# |
|||
# == Overview |
|||
# |
|||
# This file provides the +CGI::Session+ class, which provides session |
|||
# support for CGI scripts. A session is a sequence of HTTP requests |
|||
# and responses linked together and associated with a single client. |
|||
# Information associated with the session is stored |
|||
# on the server between requests. A session id is passed between client |
|||
# and server with every request and response, transparently |
|||
# to the user. This adds state information to the otherwise stateless |
|||
# HTTP request/response protocol. |
|||
# |
|||
# See the documentation to the +CGI::Session+ class for more details |
|||
# and examples of usage. See cgi.rb for the +CGI+ class itself. |
|||
|
|||
require 'cgi' |
|||
require 'tmpdir' |
|||
|
|||
class CGI |
|||
|
|||
# Class representing an HTTP session. See documentation for the file |
|||
# cgi/session.rb for an introduction to HTTP sessions. |
|||
# |
|||
# == Lifecycle |
|||
# |
|||
# A CGI::Session instance is created from a CGI object. By default, |
|||
# this CGI::Session instance will start a new session if none currently |
|||
# exists, or continue the current session for this client if one does |
|||
# exist. The +new_session+ option can be used to either always or |
|||
# never create a new session. See #new() for more details. |
|||
# |
|||
# #delete() deletes a session from session storage. It |
|||
# does not however remove the session id from the client. If the client |
|||
# makes another request with the same id, the effect will be to start |
|||
# a new session with the old session's id. |
|||
# |
|||
# == Setting and retrieving session data. |
|||
# |
|||
# The Session class associates data with a session as key-value pairs. |
|||
# This data can be set and retrieved by indexing the Session instance |
|||
# using '[]', much the same as hashes (although other hash methods |
|||
# are not supported). |
|||
# |
|||
# When session processing has been completed for a request, the |
|||
# session should be closed using the close() method. This will |
|||
# store the session's state to persistent storage. If you want |
|||
# to store the session's state to persistent storage without |
|||
# finishing session processing for this request, call the update() |
|||
# method. |
|||
# |
|||
# == Storing session state |
|||
# |
|||
# The caller can specify what form of storage to use for the session's |
|||
# data with the +database_manager+ option to CGI::Session::new. The |
|||
# following storage classes are provided as part of the standard library: |
|||
# |
|||
# CGI::Session::FileStore:: stores data as plain text in a flat file. Only |
|||
# works with String data. This is the default |
|||
# storage type. |
|||
# CGI::Session::MemoryStore:: stores data in an in-memory hash. The data |
|||
# only persists for as long as the current ruby |
|||
# interpreter instance does. |
|||
# CGI::Session::PStore:: stores data in Marshalled format. Provided by |
|||
# cgi/session/pstore.rb. Supports data of any type, |
|||
# and provides file-locking and transaction support. |
|||
# |
|||
# Custom storage types can also be created by defining a class with |
|||
# the following methods: |
|||
# |
|||
# new(session, options) |
|||
# restore # returns hash of session data. |
|||
# update |
|||
# close |
|||
# delete |
|||
# |
|||
# Changing storage type mid-session does not work. Note in particular |
|||
# that by default the FileStore and PStore session data files have the |
|||
# same name. If your application switches from one to the other without |
|||
# making sure that filenames will be different |
|||
# and clients still have old sessions lying around in cookies, then |
|||
# things will break nastily! |
|||
# |
|||
# == Maintaining the session id. |
|||
# |
|||
# Most session state is maintained on the server. However, a session |
|||
# id must be passed backwards and forwards between client and server |
|||
# to maintain a reference to this session state. |
|||
# |
|||
# The simplest way to do this is via cookies. The CGI::Session class |
|||
# provides transparent support for session id communication via cookies |
|||
# if the client has cookies enabled. |
|||
# |
|||
# If the client has cookies disabled, the session id must be included |
|||
# as a parameter of all requests sent by the client to the server. The |
|||
# CGI::Session class in conjunction with the CGI class will transparently |
|||
# add the session id as a hidden input field to all forms generated |
|||
# using the CGI#form() HTML generation method. No built-in support is |
|||
# provided for other mechanisms, such as URL re-writing. The caller is |
|||
# responsible for extracting the session id from the session_id |
|||
# attribute and manually encoding it in URLs and adding it as a hidden |
|||
# input to HTML forms created by other mechanisms. Also, session expiry |
|||
# is not automatically handled. |
|||
# |
|||
# == Examples of use |
|||
# |
|||
# === Setting the user's name |
|||
# |
|||
# require 'cgi' |
|||
# require 'cgi/session' |
|||
# require 'cgi/session/pstore' # provides CGI::Session::PStore |
|||
# |
|||
# cgi = CGI.new("html4") |
|||
# |
|||
# session = CGI::Session.new(cgi, |
|||
# 'database_manager' => CGI::Session::PStore, # use PStore |
|||
# 'session_key' => '_rb_sess_id', # custom session key |
|||
# 'session_expires' => Time.now + 30 * 60, # 30 minute timeout |
|||
# 'prefix' => 'pstore_sid_') # PStore option |
|||
# if cgi.has_key?('user_name') and cgi['user_name'] != '' |
|||
# # coerce to String: cgi[] returns the |
|||
# # string-like CGI::QueryExtension::Value |
|||
# session['user_name'] = cgi['user_name'].to_s |
|||
# elsif !session['user_name'] |
|||
# session['user_name'] = "guest" |
|||
# end |
|||
# session.close |
|||
# |
|||
# === Creating a new session safely |
|||
# |
|||
# require 'cgi' |
|||
# require 'cgi/session' |
|||
# |
|||
# cgi = CGI.new("html4") |
|||
# |
|||
# # We make sure to delete an old session if one exists, |
|||
# # not just to free resources, but to prevent the session |
|||
# # from being maliciously hijacked later on. |
|||
# begin |
|||
# session = CGI::Session.new(cgi, 'new_session' => false) |
|||
# session.delete |
|||
# rescue ArgumentError # if no old session |
|||
# end |
|||
# session = CGI::Session.new(cgi, 'new_session' => true) |
|||
# session.close |
|||
# |
|||
class Session |
|||
|
|||
class NoSession < RuntimeError #:nodoc: |
|||
end |
|||
|
|||
# The id of this session. |
|||
attr_reader :session_id, :new_session |
|||
|
|||
def Session::callback(dbman) #:nodoc: |
|||
Proc.new{ |
|||
dbman[0].close unless dbman.empty? |
|||
} |
|||
end |
|||
|
|||
# Create a new session id. |
|||
# |
|||
# The session id is an MD5 hash based upon the time, |
|||
# a random number, and a constant string. This routine |
|||
# is used internally for automatically generated |
|||
# session ids. |
|||
def create_new_id |
|||
require 'digest/md5' |
|||
md5 = Digest::MD5::new |
|||
now = Time::now |
|||
md5.update(now.to_s) |
|||
md5.update(String(now.usec)) |
|||
md5.update(String(rand(0))) |
|||
md5.update(String($$)) |
|||
md5.update('foobar') |
|||
@new_session = true |
|||
md5.hexdigest |
|||
end |
|||
private :create_new_id |
|||
|
|||
# Create a new CGI::Session object for +request+. |
|||
# |
|||
# +request+ is an instance of the +CGI+ class (see cgi.rb). |
|||
# +option+ is a hash of options for initialising this |
|||
# CGI::Session instance. The following options are |
|||
# recognised: |
|||
# |
|||
# session_key:: the parameter name used for the session id. |
|||
# Defaults to '_session_id'. |
|||
# session_id:: the session id to use. If not provided, then |
|||
# it is retrieved from the +session_key+ parameter |
|||
# of the request, or automatically generated for |
|||
# a new session. |
|||
# new_session:: if true, force creation of a new session. If not set, |
|||
# a new session is only created if none currently |
|||
# exists. If false, a new session is never created, |
|||
# and if none currently exists and the +session_id+ |
|||
# option is not set, an ArgumentError is raised. |
|||
# database_manager:: the name of the class providing storage facilities |
|||
# for session state persistence. Built-in support |
|||
# is provided for +FileStore+ (the default), |
|||
# +MemoryStore+, and +PStore+ (from |
|||
# cgi/session/pstore.rb). See the documentation for |
|||
# these classes for more details. |
|||
# |
|||
# The following options are also recognised, but only apply if the |
|||
# session id is stored in a cookie. |
|||
# |
|||
# session_expires:: the time the current session expires, as a |
|||
# +Time+ object. If not set, the session will terminate |
|||
# when the user's browser is closed. |
|||
# session_domain:: the hostname domain for which this session is valid. |
|||
# If not set, defaults to the hostname of the server. |
|||
# session_secure:: if +true+, this session will only work over HTTPS. |
|||
# session_path:: the path for which this session applies. Defaults |
|||
# to the directory of the CGI script. |
|||
# |
|||
# +option+ is also passed on to the session storage class initialiser; see |
|||
# the documentation for each session storage class for the options |
|||
# they support. |
|||
# |
|||
# The retrieved or created session is automatically added to +request+ |
|||
# as a cookie, and also to its +output_hidden+ table, which is used |
|||
# to add hidden input elements to forms. |
|||
# |
|||
# *WARNING* the +output_hidden+ |
|||
# fields are surrounded by a <fieldset> tag in HTML 4 generation, which |
|||
# is _not_ invisible on many browsers; you may wish to disable the |
|||
# use of fieldsets with code similar to the following |
|||
# (see http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-list/37805) |
|||
# |
|||
# cgi = CGI.new("html4") |
|||
# class << cgi |
|||
# undef_method :fieldset |
|||
# end |
|||
# |
|||
def initialize(request, option={}) |
|||
@new_session = false |
|||
session_key = option['session_key'] || '_session_id' |
|||
session_id = option['session_id'] |
|||
unless session_id |
|||
if option['new_session'] |
|||
session_id = create_new_id |
|||
end |
|||
end |
|||
unless session_id |
|||
if request.key?(session_key) |
|||
session_id = request[session_key] |
|||
session_id = session_id.read if session_id.respond_to?(:read) |
|||
end |
|||
unless session_id |
|||
session_id, = request.cookies[session_key] |
|||
end |
|||
unless session_id |
|||
unless option.fetch('new_session', true) |
|||
raise ArgumentError, "session_key `%s' should be supplied"%session_key |
|||
end |
|||
session_id = create_new_id |
|||
end |
|||
end |
|||
@session_id = session_id |
|||
dbman = option['database_manager'] || FileStore |
|||
begin |
|||
@dbman = dbman::new(self, option) |
|||
rescue NoSession |
|||
unless option.fetch('new_session', true) |
|||
raise ArgumentError, "invalid session_id `%s'"%session_id |
|||
end |
|||
session_id = @session_id = create_new_id |
|||
retry |
|||
end |
|||
request.instance_eval do |
|||
@output_hidden = {session_key => session_id} unless option['no_hidden'] |
|||
@output_cookies = [ |
|||
Cookie::new("name" => session_key, |
|||
"value" => session_id, |
|||
"expires" => option['session_expires'], |
|||
"domain" => option['session_domain'], |
|||
"secure" => option['session_secure'], |
|||
"path" => if option['session_path'] then |
|||
option['session_path'] |
|||
elsif ENV["SCRIPT_NAME"] then |
|||
File::dirname(ENV["SCRIPT_NAME"]) |
|||
else |
|||
"" |
|||
end) |
|||
] unless option['no_cookies'] |
|||
end |
|||
@dbprot = [@dbman] |
|||
ObjectSpace::define_finalizer(self, Session::callback(@dbprot)) |
|||
end |
|||
|
|||
# Retrieve the session data for key +key+. |
|||
def [](key) |
|||
@data ||= @dbman.restore |
|||
@data[key] |
|||
end |
|||
|
|||
# Set the session date for key +key+. |
|||
def []=(key, val) |
|||
@write_lock ||= true |
|||
@data ||= @dbman.restore |
|||
@data[key] = val |
|||
end |
|||
|
|||
# Store session data on the server. For some session storage types, |
|||
# this is a no-op. |
|||
def update |
|||
@dbman.update |
|||
end |
|||
|
|||
# Store session data on the server and close the session storage. |
|||
# For some session storage types, this is a no-op. |
|||
def close |
|||
@dbman.close |
|||
@dbprot.clear |
|||
end |
|||
|
|||
# Delete the session from storage. Also closes the storage. |
|||
# |
|||
# Note that the session's data is _not_ automatically deleted |
|||
# upon the session expiring. |
|||
def delete |
|||
@dbman.delete |
|||
@dbprot.clear |
|||
end |
|||
|
|||
# File-based session storage class. |
|||
# |
|||
# Implements session storage as a flat file of 'key=value' values. |
|||
# This storage type only works directly with String values; the |
|||
# user is responsible for converting other types to Strings when |
|||
# storing and from Strings when retrieving. |
|||
class FileStore |
|||
# Create a new FileStore instance. |
|||
# |
|||
# This constructor is used internally by CGI::Session. The |
|||
# user does not generally need to call it directly. |
|||
# |
|||
# +session+ is the session for which this instance is being |
|||
# created. The session id must only contain alphanumeric |
|||
# characters; automatically generated session ids observe |
|||
# this requirement. |
|||
# |
|||
# +option+ is a hash of options for the initialiser. The |
|||
# following options are recognised: |
|||
# |
|||
# tmpdir:: the directory to use for storing the FileStore |
|||
# file. Defaults to Dir::tmpdir (generally "/tmp" |
|||
# on Unix systems). |
|||
# prefix:: the prefix to add to the session id when generating |
|||
# the filename for this session's FileStore file. |
|||
# Defaults to the empty string. |
|||
# suffix:: the prefix to add to the session id when generating |
|||
# the filename for this session's FileStore file. |
|||
# Defaults to the empty string. |
|||
# |
|||
# This session's FileStore file will be created if it does |
|||
# not exist, or opened if it does. |
|||
def initialize(session, option={}) |
|||
dir = option['tmpdir'] || Dir::tmpdir |
|||
prefix = option['prefix'] || '' |
|||
suffix = option['suffix'] || '' |
|||
id = session.session_id |
|||
require 'digest/md5' |
|||
md5 = Digest::MD5.hexdigest(id)[0,16] |
|||
@path = dir+"/"+prefix+md5+suffix |
|||
if File::exist? @path |
|||
@hash = nil |
|||
else |
|||
unless session.new_session |
|||
raise CGI::Session::NoSession, "uninitialized session" |
|||
end |
|||
@hash = {} |
|||
end |
|||
end |
|||
|
|||
# Restore session state from the session's FileStore file. |
|||
# |
|||
# Returns the session state as a hash. |
|||
def restore |
|||
unless @hash |
|||
@hash = {} |
|||
begin |
|||
lockf = File.open(@path+".lock", "r") |
|||
lockf.flock File::LOCK_SH |
|||
f = File.open(@path, 'r') |
|||
for line in f |
|||
line.chomp! |
|||
k, v = line.split('=',2) |
|||
@hash[CGI::unescape(k)] = CGI::unescape(v) |
|||
end |
|||
ensure |
|||
f.close unless f.nil? |
|||
lockf.close if lockf |
|||
end |
|||
end |
|||
@hash |
|||
end |
|||
|
|||
# Save session state to the session's FileStore file. |
|||
def update |
|||
return unless @hash |
|||
begin |
|||
lockf = File.open(@path+".lock", File::CREAT|File::RDWR, 0600) |
|||
lockf.flock File::LOCK_EX |
|||
f = File.open(@path+".new", File::CREAT|File::TRUNC|File::WRONLY, 0600) |
|||
for k,v in @hash |
|||
f.printf "%s=%s\n", CGI::escape(k), CGI::escape(String(v)) |
|||
end |
|||
f.close |
|||
File.rename @path+".new", @path |
|||
ensure |
|||
f.close if f and !f.closed? |
|||
lockf.close if lockf |
|||
end |
|||
end |
|||
|
|||
# Update and close the session's FileStore file. |
|||
def close |
|||
update |
|||
end |
|||
|
|||
# Close and delete the session's FileStore file. |
|||
def delete |
|||
File::unlink @path+".lock" rescue nil |
|||
File::unlink @path+".new" rescue nil |
|||
File::unlink @path |
|||
rescue Errno::ENOENT |
|||
end |
|||
end |
|||
|
|||
# In-memory session storage class. |
|||
# |
|||
# Implements session storage as a global in-memory hash. Session |
|||
# data will only persist for as long as the ruby interpreter |
|||
# instance does. |
|||
class MemoryStore |
|||
GLOBAL_HASH_TABLE = {} #:nodoc: |
|||
|
|||
# Create a new MemoryStore instance. |
|||
# |
|||
# +session+ is the session this instance is associated with. |
|||
# +option+ is a list of initialisation options. None are |
|||
# currently recognised. |
|||
def initialize(session, option=nil) |
|||
@session_id = session.session_id |
|||
unless GLOBAL_HASH_TABLE.key?(@session_id) |
|||
unless session.new_session |
|||
raise CGI::Session::NoSession, "uninitialized session" |
|||
end |
|||
GLOBAL_HASH_TABLE[@session_id] = {} |
|||
end |
|||
end |
|||
|
|||
# Restore session state. |
|||
# |
|||
# Returns session data as a hash. |
|||
def restore |
|||
GLOBAL_HASH_TABLE[@session_id] |
|||
end |
|||
|
|||
# Update session state. |
|||
# |
|||
# A no-op. |
|||
def update |
|||
# don't need to update; hash is shared |
|||
end |
|||
|
|||
# Close session storage. |
|||
# |
|||
# A no-op. |
|||
def close |
|||
# don't need to close |
|||
end |
|||
|
|||
# Delete the session state. |
|||
def delete |
|||
GLOBAL_HASH_TABLE.delete(@session_id) |
|||
end |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,111 @@ |
|||
# |
|||
# cgi/session/pstore.rb - persistent storage of marshalled session data |
|||
# |
|||
# Documentation: William Webber (william@williamwebber.com) |
|||
# |
|||
# == Overview |
|||
# |
|||
# This file provides the CGI::Session::PStore class, which builds |
|||
# persistent of session data on top of the pstore library. See |
|||
# cgi/session.rb for more details on session storage managers. |
|||
|
|||
require 'cgi/session' |
|||
require 'pstore' |
|||
|
|||
class CGI |
|||
class Session |
|||
# PStore-based session storage class. |
|||
# |
|||
# This builds upon the top-level PStore class provided by the |
|||
# library file pstore.rb. Session data is marshalled and stored |
|||
# in a file. File locking and transaction services are provided. |
|||
class PStore |
|||
# Create a new CGI::Session::PStore instance |
|||
# |
|||
# This constructor is used internally by CGI::Session. The |
|||
# user does not generally need to call it directly. |
|||
# |
|||
# +session+ is the session for which this instance is being |
|||
# created. The session id must only contain alphanumeric |
|||
# characters; automatically generated session ids observe |
|||
# this requirement. |
|||
# |
|||
# +option+ is a hash of options for the initialiser. The |
|||
# following options are recognised: |
|||
# |
|||
# tmpdir:: the directory to use for storing the PStore |
|||
# file. Defaults to Dir::tmpdir (generally "/tmp" |
|||
# on Unix systems). |
|||
# prefix:: the prefix to add to the session id when generating |
|||
# the filename for this session's PStore file. |
|||
# Defaults to the empty string. |
|||
# |
|||
# This session's PStore file will be created if it does |
|||
# not exist, or opened if it does. |
|||
def initialize(session, option={}) |
|||
dir = option['tmpdir'] || Dir::tmpdir |
|||
prefix = option['prefix'] || '' |
|||
id = session.session_id |
|||
require 'digest/md5' |
|||
md5 = Digest::MD5.hexdigest(id)[0,16] |
|||
path = dir+"/"+prefix+md5 |
|||
path.untaint |
|||
if File::exist?(path) |
|||
@hash = nil |
|||
else |
|||
unless session.new_session |
|||
raise CGI::Session::NoSession, "uninitialized session" |
|||
end |
|||
@hash = {} |
|||
end |
|||
@p = ::PStore.new(path) |
|||
@p.transaction do |p| |
|||
File.chmod(0600, p.path) |
|||
end |
|||
end |
|||
|
|||
# Restore session state from the session's PStore file. |
|||
# |
|||
# Returns the session state as a hash. |
|||
def restore |
|||
unless @hash |
|||
@p.transaction do |
|||
@hash = @p['hash'] || {} |
|||
end |
|||
end |
|||
@hash |
|||
end |
|||
|
|||
# Save session state to the session's PStore file. |
|||
def update |
|||
@p.transaction do |
|||
@p['hash'] = @hash |
|||
end |
|||
end |
|||
|
|||
# Update and close the session's PStore file. |
|||
def close |
|||
update |
|||
end |
|||
|
|||
# Close and delete the session's PStore file. |
|||
def delete |
|||
path = @p.path |
|||
File::unlink path |
|||
end |
|||
|
|||
end |
|||
end |
|||
end |
|||
|
|||
if $0 == __FILE__ |
|||
# :enddoc: |
|||
STDIN.reopen("/dev/null") |
|||
cgi = CGI.new |
|||
session = CGI::Session.new(cgi, 'database_manager' => CGI::Session::PStore) |
|||
session['key'] = {'k' => 'v'} |
|||
puts session['key'].class |
|||
fail unless Hash === session['key'] |
|||
puts session['key'].inspect |
|||
fail unless session['key'].inspect == '{"k"=>"v"}' |
|||
end |
|||
@ -0,0 +1,631 @@ |
|||
# |
|||
# complex.rb - |
|||
# $Release Version: 0.5 $ |
|||
# $Revision: 1.3 $ |
|||
# $Date: 1998/07/08 10:05:28 $ |
|||
# by Keiju ISHITSUKA(SHL Japan Inc.) |
|||
# |
|||
# ---- |
|||
# |
|||
# complex.rb implements the Complex class for complex numbers. Additionally, |
|||
# some methods in other Numeric classes are redefined or added to allow greater |
|||
# interoperability with Complex numbers. |
|||
# |
|||
# Complex numbers can be created in the following manner: |
|||
# - <tt>Complex(a, b)</tt> |
|||
# - <tt>Complex.polar(radius, theta)</tt> |
|||
# |
|||
# Additionally, note the following: |
|||
# - <tt>Complex::I</tt> (the mathematical constant <i>i</i>) |
|||
# - <tt>Numeric#im</tt> (e.g. <tt>5.im -> 0+5i</tt>) |
|||
# |
|||
# The following +Math+ module methods are redefined to handle Complex arguments. |
|||
# They will work as normal with non-Complex arguments. |
|||
# sqrt exp cos sin tan log log10 |
|||
# cosh sinh tanh acos asin atan atan2 acosh asinh atanh |
|||
# |
|||
|
|||
|
|||
# |
|||
# Numeric is a built-in class on which Fixnum, Bignum, etc., are based. Here |
|||
# some methods are added so that all number types can be treated to some extent |
|||
# as Complex numbers. |
|||
# |
|||
class Numeric |
|||
# |
|||
# Returns a Complex number <tt>(0,<i>self</i>)</tt>. |
|||
# |
|||
def im |
|||
Complex(0, self) |
|||
end |
|||
|
|||
# |
|||
# The real part of a complex number, i.e. <i>self</i>. |
|||
# |
|||
def real |
|||
self |
|||
end |
|||
|
|||
# |
|||
# The imaginary part of a complex number, i.e. 0. |
|||
# |
|||
def image |
|||
0 |
|||
end |
|||
alias imag image |
|||
|
|||
# |
|||
# See Complex#arg. |
|||
# |
|||
def arg |
|||
if self >= 0 |
|||
return 0 |
|||
else |
|||
return Math::PI |
|||
end |
|||
end |
|||
alias angle arg |
|||
|
|||
# |
|||
# See Complex#polar. |
|||
# |
|||
def polar |
|||
return abs, arg |
|||
end |
|||
|
|||
# |
|||
# See Complex#conjugate (short answer: returns <i>self</i>). |
|||
# |
|||
def conjugate |
|||
self |
|||
end |
|||
alias conj conjugate |
|||
end |
|||
|
|||
|
|||
# |
|||
# Creates a Complex number. +a+ and +b+ should be Numeric. The result will be |
|||
# <tt>a+bi</tt>. |
|||
# |
|||
def Complex(a, b = 0) |
|||
if b == 0 and (a.kind_of?(Complex) or defined? Complex::Unify) |
|||
a |
|||
else |
|||
Complex.new( a.real-b.imag, a.imag+b.real ) |
|||
end |
|||
end |
|||
|
|||
# |
|||
# The complex number class. See complex.rb for an overview. |
|||
# |
|||
class Complex < Numeric |
|||
@RCS_ID='-$Id: complex.rb,v 1.3 1998/07/08 10:05:28 keiju Exp keiju $-' |
|||
|
|||
undef step |
|||
|
|||
def Complex.generic?(other) # :nodoc: |
|||
other.kind_of?(Integer) or |
|||
other.kind_of?(Float) or |
|||
(defined?(Rational) and other.kind_of?(Rational)) |
|||
end |
|||
|
|||
# |
|||
# Creates a +Complex+ number in terms of +r+ (radius) and +theta+ (angle). |
|||
# |
|||
def Complex.polar(r, theta) |
|||
Complex(r*Math.cos(theta), r*Math.sin(theta)) |
|||
end |
|||
|
|||
# |
|||
# Creates a +Complex+ number <tt>a</tt>+<tt>b</tt><i>i</i>. |
|||
# |
|||
def Complex.new!(a, b=0) |
|||
new(a,b) |
|||
end |
|||
|
|||
def initialize(a, b) |
|||
raise TypeError, "non numeric 1st arg `#{a.inspect}'" if !a.kind_of? Numeric |
|||
raise TypeError, "`#{a.inspect}' for 1st arg" if a.kind_of? Complex |
|||
raise TypeError, "non numeric 2nd arg `#{b.inspect}'" if !b.kind_of? Numeric |
|||
raise TypeError, "`#{b.inspect}' for 2nd arg" if b.kind_of? Complex |
|||
@real = a |
|||
@image = b |
|||
end |
|||
|
|||
# |
|||
# Addition with real or complex number. |
|||
# |
|||
def + (other) |
|||
if other.kind_of?(Complex) |
|||
re = @real + other.real |
|||
im = @image + other.image |
|||
Complex(re, im) |
|||
elsif Complex.generic?(other) |
|||
Complex(@real + other, @image) |
|||
else |
|||
x , y = other.coerce(self) |
|||
x + y |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Subtraction with real or complex number. |
|||
# |
|||
def - (other) |
|||
if other.kind_of?(Complex) |
|||
re = @real - other.real |
|||
im = @image - other.image |
|||
Complex(re, im) |
|||
elsif Complex.generic?(other) |
|||
Complex(@real - other, @image) |
|||
else |
|||
x , y = other.coerce(self) |
|||
x - y |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Multiplication with real or complex number. |
|||
# |
|||
def * (other) |
|||
if other.kind_of?(Complex) |
|||
re = @real*other.real - @image*other.image |
|||
im = @real*other.image + @image*other.real |
|||
Complex(re, im) |
|||
elsif Complex.generic?(other) |
|||
Complex(@real * other, @image * other) |
|||
else |
|||
x , y = other.coerce(self) |
|||
x * y |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Division by real or complex number. |
|||
# |
|||
def / (other) |
|||
if other.kind_of?(Complex) |
|||
self*other.conjugate/other.abs2 |
|||
elsif Complex.generic?(other) |
|||
Complex(@real/other, @image/other) |
|||
else |
|||
x, y = other.coerce(self) |
|||
x/y |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Raise this complex number to the given (real or complex) power. |
|||
# |
|||
def ** (other) |
|||
if other == 0 |
|||
return Complex(1) |
|||
end |
|||
if other.kind_of?(Complex) |
|||
r, theta = polar |
|||
ore = other.real |
|||
oim = other.image |
|||
nr = Math.exp!(ore*Math.log!(r) - oim * theta) |
|||
ntheta = theta*ore + oim*Math.log!(r) |
|||
Complex.polar(nr, ntheta) |
|||
elsif other.kind_of?(Integer) |
|||
if other > 0 |
|||
x = self |
|||
z = x |
|||
n = other - 1 |
|||
while n != 0 |
|||
while (div, mod = n.divmod(2) |
|||
mod == 0) |
|||
x = Complex(x.real*x.real - x.image*x.image, 2*x.real*x.image) |
|||
n = div |
|||
end |
|||
z *= x |
|||
n -= 1 |
|||
end |
|||
z |
|||
else |
|||
if defined? Rational |
|||
(Rational(1) / self) ** -other |
|||
else |
|||
self ** Float(other) |
|||
end |
|||
end |
|||
elsif Complex.generic?(other) |
|||
r, theta = polar |
|||
Complex.polar(r**other, theta*other) |
|||
else |
|||
x, y = other.coerce(self) |
|||
x**y |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Remainder after division by a real or complex number. |
|||
# |
|||
def % (other) |
|||
if other.kind_of?(Complex) |
|||
Complex(@real % other.real, @image % other.image) |
|||
elsif Complex.generic?(other) |
|||
Complex(@real % other, @image % other) |
|||
else |
|||
x , y = other.coerce(self) |
|||
x % y |
|||
end |
|||
end |
|||
|
|||
#-- |
|||
# def divmod(other) |
|||
# if other.kind_of?(Complex) |
|||
# rdiv, rmod = @real.divmod(other.real) |
|||
# idiv, imod = @image.divmod(other.image) |
|||
# return Complex(rdiv, idiv), Complex(rmod, rmod) |
|||
# elsif Complex.generic?(other) |
|||
# Complex(@real.divmod(other), @image.divmod(other)) |
|||
# else |
|||
# x , y = other.coerce(self) |
|||
# x.divmod(y) |
|||
# end |
|||
# end |
|||
#++ |
|||
|
|||
# |
|||
# Absolute value (aka modulus): distance from the zero point on the complex |
|||
# plane. |
|||
# |
|||
def abs |
|||
Math.hypot(@real, @image) |
|||
end |
|||
|
|||
# |
|||
# Square of the absolute value. |
|||
# |
|||
def abs2 |
|||
@real*@real + @image*@image |
|||
end |
|||
|
|||
# |
|||
# Argument (angle from (1,0) on the complex plane). |
|||
# |
|||
def arg |
|||
Math.atan2!(@image, @real) |
|||
end |
|||
alias angle arg |
|||
|
|||
# |
|||
# Returns the absolute value _and_ the argument. |
|||
# |
|||
def polar |
|||
return abs, arg |
|||
end |
|||
|
|||
# |
|||
# Complex conjugate (<tt>z + z.conjugate = 2 * z.real</tt>). |
|||
# |
|||
def conjugate |
|||
Complex(@real, -@image) |
|||
end |
|||
alias conj conjugate |
|||
|
|||
# |
|||
# Compares the absolute values of the two numbers. |
|||
# |
|||
def <=> (other) |
|||
self.abs <=> other.abs |
|||
end |
|||
|
|||
# |
|||
# Test for numerical equality (<tt>a == a + 0<i>i</i></tt>). |
|||
# |
|||
def == (other) |
|||
if other.kind_of?(Complex) |
|||
@real == other.real and @image == other.image |
|||
elsif Complex.generic?(other) |
|||
@real == other and @image == 0 |
|||
else |
|||
other == self |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Attempts to coerce +other+ to a Complex number. |
|||
# |
|||
def coerce(other) |
|||
if Complex.generic?(other) |
|||
return Complex.new!(other), self |
|||
else |
|||
super |
|||
end |
|||
end |
|||
|
|||
# |
|||
# FIXME |
|||
# |
|||
def denominator |
|||
@real.denominator.lcm(@image.denominator) |
|||
end |
|||
|
|||
# |
|||
# FIXME |
|||
# |
|||
def numerator |
|||
cd = denominator |
|||
Complex(@real.numerator*(cd/@real.denominator), |
|||
@image.numerator*(cd/@image.denominator)) |
|||
end |
|||
|
|||
# |
|||
# Standard string representation of the complex number. |
|||
# |
|||
def to_s |
|||
if @real != 0 |
|||
if defined?(Rational) and @image.kind_of?(Rational) and @image.denominator != 1 |
|||
if @image >= 0 |
|||
@real.to_s+"+("+@image.to_s+")i" |
|||
else |
|||
@real.to_s+"-("+(-@image).to_s+")i" |
|||
end |
|||
else |
|||
if @image >= 0 |
|||
@real.to_s+"+"+@image.to_s+"i" |
|||
else |
|||
@real.to_s+"-"+(-@image).to_s+"i" |
|||
end |
|||
end |
|||
else |
|||
if defined?(Rational) and @image.kind_of?(Rational) and @image.denominator != 1 |
|||
"("+@image.to_s+")i" |
|||
else |
|||
@image.to_s+"i" |
|||
end |
|||
end |
|||
end |
|||
|
|||
# |
|||
# Returns a hash code for the complex number. |
|||
# |
|||
def hash |
|||
@real.hash ^ @image.hash |
|||
end |
|||
|
|||
# |
|||
# Returns "<tt>Complex(<i>real</i>, <i>image</i>)</tt>". |
|||
# |
|||
def inspect |
|||
sprintf("Complex(%s, %s)", @real.inspect, @image.inspect) |
|||
end |
|||
|
|||
|
|||
# |
|||
# +I+ is the imaginary number. It exists at point (0,1) on the complex plane. |
|||
# |
|||
I = Complex(0,1) |
|||
|
|||
# The real part of a complex number. |
|||
attr :real |
|||
|
|||
# The imaginary part of a complex number. |
|||
attr :image |
|||
alias imag image |
|||
|
|||
end |
|||
|
|||
|
|||
|
|||
|
|||
module Math |
|||
alias sqrt! sqrt |
|||
alias exp! exp |
|||
alias log! log |
|||
alias log10! log10 |
|||
alias cos! cos |
|||
alias sin! sin |
|||
alias tan! tan |
|||
alias cosh! cosh |
|||
alias sinh! sinh |
|||
alias tanh! tanh |
|||
alias acos! acos |
|||
alias asin! asin |
|||
alias atan! atan |
|||
alias atan2! atan2 |
|||
alias acosh! acosh |
|||
alias asinh! asinh |
|||
alias atanh! atanh |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def sqrt(z) |
|||
if Complex.generic?(z) |
|||
if z >= 0 |
|||
sqrt!(z) |
|||
else |
|||
Complex(0,sqrt!(-z)) |
|||
end |
|||
else |
|||
if z.image < 0 |
|||
sqrt(z.conjugate).conjugate |
|||
else |
|||
r = z.abs |
|||
x = z.real |
|||
Complex( sqrt!((r+x)/2), sqrt!((r-x)/2) ) |
|||
end |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def exp(z) |
|||
if Complex.generic?(z) |
|||
exp!(z) |
|||
else |
|||
Complex(exp!(z.real) * cos!(z.image), exp!(z.real) * sin!(z.image)) |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def cos(z) |
|||
if Complex.generic?(z) |
|||
cos!(z) |
|||
else |
|||
Complex(cos!(z.real)*cosh!(z.image), |
|||
-sin!(z.real)*sinh!(z.image)) |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def sin(z) |
|||
if Complex.generic?(z) |
|||
sin!(z) |
|||
else |
|||
Complex(sin!(z.real)*cosh!(z.image), |
|||
cos!(z.real)*sinh!(z.image)) |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def tan(z) |
|||
if Complex.generic?(z) |
|||
tan!(z) |
|||
else |
|||
sin(z)/cos(z) |
|||
end |
|||
end |
|||
|
|||
def sinh(z) |
|||
if Complex.generic?(z) |
|||
sinh!(z) |
|||
else |
|||
Complex( sinh!(z.real)*cos!(z.image), cosh!(z.real)*sin!(z.image) ) |
|||
end |
|||
end |
|||
|
|||
def cosh(z) |
|||
if Complex.generic?(z) |
|||
cosh!(z) |
|||
else |
|||
Complex( cosh!(z.real)*cos!(z.image), sinh!(z.real)*sin!(z.image) ) |
|||
end |
|||
end |
|||
|
|||
def tanh(z) |
|||
if Complex.generic?(z) |
|||
tanh!(z) |
|||
else |
|||
sinh(z)/cosh(z) |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def log(z) |
|||
if Complex.generic?(z) and z >= 0 |
|||
log!(z) |
|||
else |
|||
r, theta = z.polar |
|||
Complex(log!(r.abs), theta) |
|||
end |
|||
end |
|||
|
|||
# Redefined to handle a Complex argument. |
|||
def log10(z) |
|||
if Complex.generic?(z) |
|||
log10!(z) |
|||
else |
|||
log(z)/log!(10) |
|||
end |
|||
end |
|||
|
|||
def acos(z) |
|||
if Complex.generic?(z) and z >= -1 and z <= 1 |
|||
acos!(z) |
|||
else |
|||
-1.0.im * log( z + 1.0.im * sqrt(1.0-z*z) ) |
|||
end |
|||
end |
|||
|
|||
def asin(z) |
|||
if Complex.generic?(z) and z >= -1 and z <= 1 |
|||
asin!(z) |
|||
else |
|||
-1.0.im * log( 1.0.im * z + sqrt(1.0-z*z) ) |
|||
end |
|||
end |
|||
|
|||
def atan(z) |
|||
if Complex.generic?(z) |
|||
atan!(z) |
|||
else |
|||
1.0.im * log( (1.0.im+z) / (1.0.im-z) ) / 2.0 |
|||
end |
|||
end |
|||
|
|||
def atan2(y,x) |
|||
if Complex.generic?(y) and Complex.generic?(x) |
|||
atan2!(y,x) |
|||
else |
|||
-1.0.im * log( (x+1.0.im*y) / sqrt(x*x+y*y) ) |
|||
end |
|||
end |
|||
|
|||
def acosh(z) |
|||
if Complex.generic?(z) and z >= 1 |
|||
acosh!(z) |
|||
else |
|||
log( z + sqrt(z*z-1.0) ) |
|||
end |
|||
end |
|||
|
|||
def asinh(z) |
|||
if Complex.generic?(z) |
|||
asinh!(z) |
|||
else |
|||
log( z + sqrt(1.0+z*z) ) |
|||
end |
|||
end |
|||
|
|||
def atanh(z) |
|||
if Complex.generic?(z) and z >= -1 and z <= 1 |
|||
atanh!(z) |
|||
else |
|||
log( (1.0+z) / (1.0-z) ) / 2.0 |
|||
end |
|||
end |
|||
|
|||
module_function :sqrt! |
|||
module_function :sqrt |
|||
module_function :exp! |
|||
module_function :exp |
|||
module_function :log! |
|||
module_function :log |
|||
module_function :log10! |
|||
module_function :log10 |
|||
module_function :cosh! |
|||
module_function :cosh |
|||
module_function :cos! |
|||
module_function :cos |
|||
module_function :sinh! |
|||
module_function :sinh |
|||
module_function :sin! |
|||
module_function :sin |
|||
module_function :tan! |
|||
module_function :tan |
|||
module_function :tanh! |
|||
module_function :tanh |
|||
module_function :acos! |
|||
module_function :acos |
|||
module_function :asin! |
|||
module_function :asin |
|||
module_function :atan! |
|||
module_function :atan |
|||
module_function :atan2! |
|||
module_function :atan2 |
|||
module_function :acosh! |
|||
module_function :acosh |
|||
module_function :asinh! |
|||
module_function :asinh |
|||
module_function :atanh! |
|||
module_function :atanh |
|||
|
|||
end |
|||
|
|||
# Documentation comments: |
|||
# - source: original (researched from pickaxe) |
|||
# - a couple of fixme's |
|||
# - RDoc output for Bignum etc. is a bit short, with nothing but an |
|||
# (undocumented) alias. No big deal. |
|||
@ -0,0 +1,992 @@ |
|||
# CSV -- module for generating/parsing CSV data. |
|||
# Copyright (C) 2000-2004 NAKAMURA, Hiroshi <nakahiro@sarion.co.jp>. |
|||
|
|||
# $Id: csv.rb 11708 2007-02-12 23:01:19Z shyouhei $ |
|||
|
|||
# This program is copyrighted free software by NAKAMURA, Hiroshi. You can |
|||
# redistribute it and/or modify it under the same terms of Ruby's license; |
|||
# either the dual license version in 2003, or any later version. |
|||
|
|||
|
|||
class CSV |
|||
class IllegalFormatError < RuntimeError; end |
|||
|
|||
# deprecated |
|||
class Cell < String |
|||
def initialize(data = "", is_null = false) |
|||
super(is_null ? "" : data) |
|||
end |
|||
|
|||
def data |
|||
to_s |
|||
end |
|||
end |
|||
|
|||
# deprecated |
|||
class Row < Array |
|||
end |
|||
|
|||
# Open a CSV formatted file for reading or writing. |
|||
# |
|||
# For reading. |
|||
# |
|||
# EXAMPLE 1 |
|||
# CSV.open('csvfile.csv', 'r') do |row| |
|||
# p row |
|||
# end |
|||
# |
|||
# EXAMPLE 2 |
|||
# reader = CSV.open('csvfile.csv', 'r') |
|||
# row1 = reader.shift |
|||
# row2 = reader.shift |
|||
# if row2.empty? |
|||
# p 'row2 not find.' |
|||
# end |
|||
# reader.close |
|||
# |
|||
# ARGS |
|||
# filename: filename to parse. |
|||
# col_sep: Column separator. ?, by default. If you want to separate |
|||
# fields with semicolon, give ?; here. |
|||
# row_sep: Row separator. nil by default. nil means "\r\n or \n". If you |
|||
# want to separate records with \r, give ?\r here. |
|||
# |
|||
# RETURNS |
|||
# reader instance. To get parse result, see CSV::Reader#each. |
|||
# |
|||
# |
|||
# For writing. |
|||
# |
|||
# EXAMPLE 1 |
|||
# CSV.open('csvfile.csv', 'w') do |writer| |
|||
# writer << ['r1c1', 'r1c2'] |
|||
# writer << ['r2c1', 'r2c2'] |
|||
# writer << [nil, nil] |
|||
# end |
|||
# |
|||
# EXAMPLE 2 |
|||
# writer = CSV.open('csvfile.csv', 'w') |
|||
# writer << ['r1c1', 'r1c2'] << ['r2c1', 'r2c2'] << [nil, nil] |
|||
# writer.close |
|||
# |
|||
# ARGS |
|||
# filename: filename to generate. |
|||
# col_sep: Column separator. ?, by default. If you want to separate |
|||
# fields with semicolon, give ?; here. |
|||
# row_sep: Row separator. nil by default. nil means "\r\n or \n". If you |
|||
# want to separate records with \r, give ?\r here. |
|||
# |
|||
# RETURNS |
|||
# writer instance. See CSV::Writer#<< and CSV::Writer#add_row to know how |
|||
# to generate CSV string. |
|||
# |
|||
def CSV.open(path, mode, fs = nil, rs = nil, &block) |
|||
if mode == 'r' or mode == 'rb' |
|||
open_reader(path, mode, fs, rs, &block) |
|||
elsif mode == 'w' or mode == 'wb' |
|||
open_writer(path, mode, fs, rs, &block) |
|||
else |
|||
raise ArgumentError.new("'mode' must be 'r', 'rb', 'w', or 'wb'") |
|||
end |
|||
end |
|||
|
|||
def CSV.foreach(path, rs = nil, &block) |
|||
open_reader(path, 'r', ',', rs, &block) |
|||
end |
|||
|
|||
def CSV.read(path, length = nil, offset = nil) |
|||
CSV.parse(IO.read(path, length, offset)) |
|||
end |
|||
|
|||
def CSV.readlines(path, rs = nil) |
|||
reader = open_reader(path, 'r', ',', rs) |
|||
begin |
|||
reader.collect { |row| row } |
|||
ensure |
|||
reader.close |
|||
end |
|||
end |
|||
|
|||
def CSV.generate(path, fs = nil, rs = nil, &block) |
|||
open_writer(path, 'w', fs, rs, &block) |
|||
end |
|||
|
|||
# Parse lines from given string or stream. Return rows as an Array of Arrays. |
|||
def CSV.parse(str_or_readable, fs = nil, rs = nil, &block) |
|||
if File.exist?(str_or_readable) |
|||
STDERR.puts("CSV.parse(filename) is deprecated." + |
|||
" Use CSV.open(filename, 'r') instead.") |
|||
return open_reader(str_or_readable, 'r', fs, rs, &block) |
|||
end |
|||
if block |
|||
CSV::Reader.parse(str_or_readable, fs, rs) do |row| |
|||
yield(row) |
|||
end |
|||
nil |
|||
else |
|||
CSV::Reader.create(str_or_readable, fs, rs).collect { |row| row } |
|||
end |
|||
end |
|||
|
|||
# Parse a line from given string. Bear in mind it parses ONE LINE. Rest of |
|||
# the string is ignored for example "a,b\r\nc,d" => ['a', 'b'] and the |
|||
# second line 'c,d' is ignored. |
|||
# |
|||
# If you don't know whether a target string to parse is exactly 1 line or |
|||
# not, use CSV.parse_row instead of this method. |
|||
def CSV.parse_line(src, fs = nil, rs = nil) |
|||
fs ||= ',' |
|||
if fs.is_a?(Fixnum) |
|||
fs = fs.chr |
|||
end |
|||
if !rs.nil? and rs.is_a?(Fixnum) |
|||
rs = rs.chr |
|||
end |
|||
idx = 0 |
|||
res_type = :DT_COLSEP |
|||
row = [] |
|||
begin |
|||
while res_type == :DT_COLSEP |
|||
res_type, idx, cell = parse_body(src, idx, fs, rs) |
|||
row << cell |
|||
end |
|||
rescue IllegalFormatError |
|||
return [] |
|||
end |
|||
row |
|||
end |
|||
|
|||
# Create a line from cells. each cell is stringified by to_s. |
|||
def CSV.generate_line(row, fs = nil, rs = nil) |
|||
if row.size == 0 |
|||
return '' |
|||
end |
|||
fs ||= ',' |
|||
if fs.is_a?(Fixnum) |
|||
fs = fs.chr |
|||
end |
|||
if !rs.nil? and rs.is_a?(Fixnum) |
|||
rs = rs.chr |
|||
end |
|||
res_type = :DT_COLSEP |
|||
result_str = '' |
|||
idx = 0 |
|||
while true |
|||
generate_body(row[idx], result_str, fs, rs) |
|||
idx += 1 |
|||
if (idx == row.size) |
|||
break |
|||
end |
|||
generate_separator(:DT_COLSEP, result_str, fs, rs) |
|||
end |
|||
result_str |
|||
end |
|||
|
|||
# Parse a line from string. Consider using CSV.parse_line instead. |
|||
# To parse lines in CSV string, see EXAMPLE below. |
|||
# |
|||
# EXAMPLE |
|||
# src = "a,b\r\nc,d\r\ne,f" |
|||
# idx = 0 |
|||
# begin |
|||
# parsed = [] |
|||
# parsed_cells, idx = CSV.parse_row(src, idx, parsed) |
|||
# puts "Parsed #{ parsed_cells } cells." |
|||
# p parsed |
|||
# end while parsed_cells > 0 |
|||
# |
|||
# ARGS |
|||
# src: a CSV data to be parsed. Must respond '[](idx)'. |
|||
# src[](idx) must return a char. (Not a string such as 'a', but 97). |
|||
# src[](idx_out_of_bounds) must return nil. A String satisfies this |
|||
# requirement. |
|||
# idx: index of parsing location of 'src'. 0 origin. |
|||
# out_dev: buffer for parsed cells. Must respond '<<(aString)'. |
|||
# col_sep: Column separator. ?, by default. If you want to separate |
|||
# fields with semicolon, give ?; here. |
|||
# row_sep: Row separator. nil by default. nil means "\r\n or \n". If you |
|||
# want to separate records with \r, give ?\r here. |
|||
# |
|||
# RETURNS |
|||
# parsed_cells: num of parsed cells. |
|||
# idx: index of next parsing location of 'src'. |
|||
# |
|||
def CSV.parse_row(src, idx, out_dev, fs = nil, rs = nil) |
|||
fs ||= ',' |
|||
if fs.is_a?(Fixnum) |
|||
fs = fs.chr |
|||
end |
|||
if !rs.nil? and rs.is_a?(Fixnum) |
|||
rs = rs.chr |
|||
end |
|||
idx_backup = idx |
|||
parsed_cells = 0 |
|||
res_type = :DT_COLSEP |
|||
begin |
|||
while res_type != :DT_ROWSEP |
|||
res_type, idx, cell = parse_body(src, idx, fs, rs) |
|||
if res_type == :DT_EOS |
|||
if idx == idx_backup #((parsed_cells == 0) and cell.nil?) |
|||
return 0, 0 |
|||
end |
|||
res_type = :DT_ROWSEP |
|||
end |
|||
parsed_cells += 1 |
|||
out_dev << cell |
|||
end |
|||
rescue IllegalFormatError |
|||
return 0, 0 |
|||
end |
|||
return parsed_cells, idx |
|||
end |
|||
|
|||
# Convert a line from cells data to string. Consider using CSV.generate_line |
|||
# instead. To generate multi-row CSV string, see EXAMPLE below. |
|||
# |
|||
# EXAMPLE |
|||
# row1 = ['a', 'b'] |
|||
# row2 = ['c', 'd'] |
|||
# row3 = ['e', 'f'] |
|||
# src = [row1, row2, row3] |
|||
# buf = '' |
|||
# src.each do |row| |
|||
# parsed_cells = CSV.generate_row(row, 2, buf) |
|||
# puts "Created #{ parsed_cells } cells." |
|||
# end |
|||
# p buf |
|||
# |
|||
# ARGS |
|||
# src: an Array of String to be converted to CSV string. Must respond to |
|||
# 'size' and '[](idx)'. src[idx] must return String. |
|||
# cells: num of cells in a line. |
|||
# out_dev: buffer for generated CSV string. Must respond to '<<(string)'. |
|||
# col_sep: Column separator. ?, by default. If you want to separate |
|||
# fields with semicolon, give ?; here. |
|||
# row_sep: Row separator. nil by default. nil means "\r\n or \n". If you |
|||
# want to separate records with \r, give ?\r here. |
|||
# |
|||
# RETURNS |
|||
# parsed_cells: num of converted cells. |
|||
# |
|||
def CSV.generate_row(src, cells, out_dev, fs = nil, rs = nil) |
|||
fs ||= ',' |
|||
if fs.is_a?(Fixnum) |
|||
fs = fs.chr |
|||
end |
|||
if !rs.nil? and rs.is_a?(Fixnum) |
|||
rs = rs.chr |
|||
end |
|||
src_size = src.size |
|||
if (src_size == 0) |
|||
if cells == 0 |
|||
generate_separator(:DT_ROWSEP, out_dev, fs, rs) |
|||
end |
|||
return 0 |
|||
end |
|||
res_type = :DT_COLSEP |
|||
parsed_cells = 0 |
|||
generate_body(src[parsed_cells], out_dev, fs, rs) |
|||
parsed_cells += 1 |
|||
while ((parsed_cells < cells) and (parsed_cells != src_size)) |
|||
generate_separator(:DT_COLSEP, out_dev, fs, rs) |
|||
generate_body(src[parsed_cells], out_dev, fs, rs) |
|||
parsed_cells += 1 |
|||
end |
|||
if (parsed_cells == cells) |
|||
generate_separator(:DT_ROWSEP, out_dev, fs, rs) |
|||
else |
|||
generate_separator(:DT_COLSEP, out_dev, fs, rs) |
|||
end |
|||
parsed_cells |
|||
end |
|||
|
|||
# Private class methods. |
|||
class << self |
|||
private |
|||
|
|||
def open_reader(path, mode, fs, rs, &block) |
|||
file = File.open(path, mode) |
|||
if block |
|||
begin |
|||
CSV::Reader.parse(file, fs, rs) do |row| |
|||
yield(row) |
|||
end |
|||
ensure |
|||
file.close |
|||
end |
|||
nil |
|||
else |
|||
reader = CSV::Reader.create(file, fs, rs) |
|||
reader.close_on_terminate |
|||
reader |
|||
end |
|||
end |
|||
|
|||
def open_writer(path, mode, fs, rs, &block) |
|||
file = File.open(path, mode) |
|||
if block |
|||
begin |
|||
CSV::Writer.generate(file, fs, rs) do |writer| |
|||
yield(writer) |
|||
end |
|||
ensure |
|||
file.close |
|||
end |
|||
nil |
|||
else |
|||
writer = CSV::Writer.create(file, fs, rs) |
|||
writer.close_on_terminate |
|||
writer |
|||
end |
|||
end |
|||
|
|||
def parse_body(src, idx, fs, rs) |
|||
fs_str = fs |
|||
fs_size = fs_str.size |
|||
rs_str = rs || "\n" |
|||
rs_size = rs_str.size |
|||
fs_idx = rs_idx = 0 |
|||
cell = Cell.new |
|||
state = :ST_START |
|||
quoted = cr = false |
|||
c = nil |
|||
last_idx = idx |
|||
while c = src[idx] |
|||
unless quoted |
|||
fschar = (c == fs_str[fs_idx]) |
|||
rschar = (c == rs_str[rs_idx]) |
|||
# simple 1 char backtrack |
|||
if !fschar and c == fs_str[0] |
|||
fs_idx = 0 |
|||
fschar = true |
|||
if state == :ST_START |
|||
state = :ST_DATA |
|||
elsif state == :ST_QUOTE |
|||
raise IllegalFormatError |
|||
end |
|||
end |
|||
if !rschar and c == rs_str[0] |
|||
rs_idx = 0 |
|||
rschar = true |
|||
if state == :ST_START |
|||
state = :ST_DATA |
|||
elsif state == :ST_QUOTE |
|||
raise IllegalFormatError |
|||
end |
|||
end |
|||
end |
|||
if c == ?" |
|||
fs_idx = rs_idx = 0 |
|||
if cr |
|||
raise IllegalFormatError |
|||
end |
|||
cell << src[last_idx, (idx - last_idx)] |
|||
last_idx = idx |
|||
if state == :ST_DATA |
|||
if quoted |
|||
last_idx += 1 |
|||
quoted = false |
|||
state = :ST_QUOTE |
|||
else |
|||
raise IllegalFormatError |
|||
end |
|||
elsif state == :ST_QUOTE |
|||
cell << c.chr |
|||
last_idx += 1 |
|||
quoted = true |
|||
state = :ST_DATA |
|||
else # :ST_START |
|||
quoted = true |
|||
last_idx += 1 |
|||
state = :ST_DATA |
|||
end |
|||
elsif fschar or rschar |
|||
if fschar |
|||
fs_idx += 1 |
|||
end |
|||
if rschar |
|||
rs_idx += 1 |
|||
end |
|||
sep = nil |
|||
if fs_idx == fs_size |
|||
if state == :ST_START and rs_idx > 0 and fs_idx < rs_idx |
|||
state = :ST_DATA |
|||
end |
|||
cell << src[last_idx, (idx - last_idx - (fs_size - 1))] |
|||
last_idx = idx |
|||
fs_idx = rs_idx = 0 |
|||
if cr |
|||
raise IllegalFormatError |
|||
end |
|||
sep = :DT_COLSEP |
|||
elsif rs_idx == rs_size |
|||
if state == :ST_START and fs_idx > 0 and rs_idx < fs_idx |
|||
state = :ST_DATA |
|||
end |
|||
if !(rs.nil? and cr) |
|||
cell << src[last_idx, (idx - last_idx - (rs_size - 1))] |
|||
last_idx = idx |
|||
end |
|||
fs_idx = rs_idx = 0 |
|||
sep = :DT_ROWSEP |
|||
end |
|||
if sep |
|||
if state == :ST_DATA |
|||
return sep, idx + 1, cell; |
|||
elsif state == :ST_QUOTE |
|||
return sep, idx + 1, cell; |
|||
else # :ST_START |
|||
return sep, idx + 1, nil |
|||
end |
|||
end |
|||
elsif rs.nil? and c == ?\r |
|||
# special \r treatment for backward compatibility |
|||
fs_idx = rs_idx = 0 |
|||
if cr |
|||
raise IllegalFormatError |
|||
end |
|||
cell << src[last_idx, (idx - last_idx)] |
|||
last_idx = idx |
|||
if quoted |
|||
state = :ST_DATA |
|||
else |
|||
cr = true |
|||
end |
|||
else |
|||
fs_idx = rs_idx = 0 |
|||
if state == :ST_DATA or state == :ST_START |
|||
if cr |
|||
raise IllegalFormatError |
|||
end |
|||
state = :ST_DATA |
|||
else # :ST_QUOTE |
|||
raise IllegalFormatError |
|||
end |
|||
end |
|||
idx += 1 |
|||
end |
|||
if state == :ST_START |
|||
if fs_idx > 0 or rs_idx > 0 |
|||
state = :ST_DATA |
|||
else |
|||
return :DT_EOS, idx, nil |
|||
end |
|||
elsif quoted |
|||
raise IllegalFormatError |
|||
elsif cr |
|||
raise IllegalFormatError |
|||
end |
|||
cell << src[last_idx, (idx - last_idx)] |
|||
last_idx = idx |
|||
return :DT_EOS, idx, cell |
|||
end |
|||
|
|||
def generate_body(cell, out_dev, fs, rs) |
|||
if cell.nil? |
|||
# empty |
|||
else |
|||
cell = cell.to_s |
|||
row_data = cell.dup |
|||
if (row_data.gsub!('"', '""') or |
|||
row_data.index(fs) or |
|||
(rs and row_data.index(rs)) or |
|||
(/[\r\n]/ =~ row_data) or |
|||
(cell.empty?)) |
|||
out_dev << '"' << row_data << '"' |
|||
else |
|||
out_dev << row_data |
|||
end |
|||
end |
|||
end |
|||
|
|||
def generate_separator(type, out_dev, fs, rs) |
|||
case type |
|||
when :DT_COLSEP |
|||
out_dev << fs |
|||
when :DT_ROWSEP |
|||
out_dev << (rs || "\n") |
|||
end |
|||
end |
|||
end |
|||
|
|||
|
|||
# CSV formatted string/stream reader. |
|||
# |
|||
# EXAMPLE |
|||
# read CSV lines untill the first column is 'stop'. |
|||
# |
|||
# CSV::Reader.parse(File.open('bigdata', 'rb')) do |row| |
|||
# p row |
|||
# break if !row[0].is_null && row[0].data == 'stop' |
|||
# end |
|||
# |
|||
class Reader |
|||
include Enumerable |
|||
|
|||
# Parse CSV data and get lines. Given block is called for each parsed row. |
|||
# Block value is always nil. Rows are not cached for performance reason. |
|||
def Reader.parse(str_or_readable, fs = ',', rs = nil, &block) |
|||
reader = Reader.create(str_or_readable, fs, rs) |
|||
if block |
|||
reader.each do |row| |
|||
yield(row) |
|||
end |
|||
reader.close |
|||
nil |
|||
else |
|||
reader |
|||
end |
|||
end |
|||
|
|||
# Returns reader instance. |
|||
def Reader.create(str_or_readable, fs = ',', rs = nil) |
|||
case str_or_readable |
|||
when IO |
|||
IOReader.new(str_or_readable, fs, rs) |
|||
when String |
|||
StringReader.new(str_or_readable, fs, rs) |
|||
else |
|||
IOReader.new(str_or_readable, fs, rs) |
|||
end |
|||
end |
|||
|
|||
def each |
|||
while true |
|||
row = [] |
|||
parsed_cells = get_row(row) |
|||
if parsed_cells == 0 |
|||
break |
|||
end |
|||
yield(row) |
|||
end |
|||
nil |
|||
end |
|||
|
|||
def shift |
|||
row = [] |
|||
parsed_cells = get_row(row) |
|||
row |
|||
end |
|||
|
|||
def close |
|||
terminate |
|||
end |
|||
|
|||
private |
|||
|
|||
def initialize(dev) |
|||
raise RuntimeError.new('Do not instanciate this class directly.') |
|||
end |
|||
|
|||
def get_row(row) |
|||
raise NotImplementedError.new('Method get_row must be defined in a derived class.') |
|||
end |
|||
|
|||
def terminate |
|||
# Define if needed. |
|||
end |
|||
end |
|||
|
|||
|
|||
class StringReader < Reader |
|||
def initialize(string, fs = ',', rs = nil) |
|||
@fs = fs |
|||
@rs = rs |
|||
@dev = string |
|||
@idx = 0 |
|||
if @dev[0, 3] == "\xef\xbb\xbf" |
|||
@idx += 3 |
|||
end |
|||
end |
|||
|
|||
private |
|||
|
|||
def get_row(row) |
|||
parsed_cells, next_idx = CSV.parse_row(@dev, @idx, row, @fs, @rs) |
|||
if parsed_cells == 0 and next_idx == 0 and @idx != @dev.size |
|||
raise IllegalFormatError.new |
|||
end |
|||
@idx = next_idx |
|||
parsed_cells |
|||
end |
|||
end |
|||
|
|||
|
|||
class IOReader < Reader |
|||
def initialize(io, fs = ',', rs = nil) |
|||
@io = io |
|||
@fs = fs |
|||
@rs = rs |
|||
@dev = CSV::IOBuf.new(@io) |
|||
@idx = 0 |
|||
if @dev[0] == 0xef and @dev[1] == 0xbb and @dev[2] == 0xbf |
|||
@idx += 3 |
|||
end |
|||
@close_on_terminate = false |
|||
end |
|||
|
|||
# Tell this reader to close the IO when terminated (Triggered by invoking |
|||
# CSV::IOReader#close). |
|||
def close_on_terminate |
|||
@close_on_terminate = true |
|||
end |
|||
|
|||
private |
|||
|
|||
def get_row(row) |
|||
parsed_cells, next_idx = CSV.parse_row(@dev, @idx, row, @fs, @rs) |
|||
if parsed_cells == 0 and next_idx == 0 and !@dev.is_eos? |
|||
raise IllegalFormatError.new |
|||
end |
|||
dropped = @dev.drop(next_idx) |
|||
@idx = next_idx - dropped |
|||
parsed_cells |
|||
end |
|||
|
|||
def terminate |
|||
if @close_on_terminate |
|||
@io.close |
|||
end |
|||
|
|||
if @dev |
|||
@dev.close |
|||
end |
|||
end |
|||
end |
|||
|
|||
|
|||
# CSV formatted string/stream writer. |
|||
# |
|||
# EXAMPLE |
|||
# Write rows to 'csvout' file. |
|||
# |
|||
# outfile = File.open('csvout', 'wb') |
|||
# CSV::Writer.generate(outfile) do |csv| |
|||
# csv << ['c1', nil, '', '"', "\r\n", 'c2'] |
|||
# ... |
|||
# end |
|||
# |
|||
# outfile.close |
|||
# |
|||
class Writer |
|||
# Given block is called with the writer instance. str_or_writable must |
|||
# handle '<<(string)'. |
|||
def Writer.generate(str_or_writable, fs = ',', rs = nil, &block) |
|||
writer = Writer.create(str_or_writable, fs, rs) |
|||
if block |
|||
yield(writer) |
|||
writer.close |
|||
nil |
|||
else |
|||
writer |
|||
end |
|||
end |
|||
|
|||
# str_or_writable must handle '<<(string)'. |
|||
def Writer.create(str_or_writable, fs = ',', rs = nil) |
|||
BasicWriter.new(str_or_writable, fs, rs) |
|||
end |
|||
|
|||
# dump CSV stream to the device. argument must be an Array of String. |
|||
def <<(row) |
|||
CSV.generate_row(row, row.size, @dev, @fs, @rs) |
|||
self |
|||
end |
|||
alias add_row << |
|||
|
|||
def close |
|||
terminate |
|||
end |
|||
|
|||
private |
|||
|
|||
def initialize(dev) |
|||
raise RuntimeError.new('Do not instanciate this class directly.') |
|||
end |
|||
|
|||
def terminate |
|||
# Define if needed. |
|||
end |
|||
end |
|||
|
|||
|
|||
class BasicWriter < Writer |
|||
def initialize(str_or_writable, fs = ',', rs = nil) |
|||
@fs = fs |
|||
@rs = rs |
|||
@dev = str_or_writable |
|||
@close_on_terminate = false |
|||
end |
|||
|
|||
# Tell this writer to close the IO when terminated (Triggered by invoking |
|||
# CSV::BasicWriter#close). |
|||
def close_on_terminate |
|||
@close_on_terminate = true |
|||
end |
|||
|
|||
private |
|||
|
|||
def terminate |
|||
if @close_on_terminate |
|||
@dev.close |
|||
end |
|||
end |
|||
end |
|||
|
|||
private |
|||
|
|||
# Buffered stream. |
|||
# |
|||
# EXAMPLE 1 -- an IO. |
|||
# class MyBuf < StreamBuf |
|||
# # Do initialize myself before a super class. Super class might call my |
|||
# # method 'read'. (Could be awful for C++ user. :-) |
|||
# def initialize(s) |
|||
# @s = s |
|||
# super() |
|||
# end |
|||
# |
|||
# # define my own 'read' method. |
|||
# # CAUTION: Returning nil means EnfOfStream. |
|||
# def read(size) |
|||
# @s.read(size) |
|||
# end |
|||
# |
|||
# # release buffers. in Ruby which has GC, you do not have to call this... |
|||
# def terminate |
|||
# @s = nil |
|||
# super() |
|||
# end |
|||
# end |
|||
# |
|||
# buf = MyBuf.new(STDIN) |
|||
# my_str = '' |
|||
# p buf[0, 0] # => '' (null string) |
|||
# p buf[0] # => 97 (char code of 'a') |
|||
# p buf[0, 1] # => 'a' |
|||
# my_str = buf[0, 5] |
|||
# p my_str # => 'abcde' (5 chars) |
|||
# p buf[0, 6] # => "abcde\n" (6 chars) |
|||
# p buf[0, 7] # => "abcde\n" (6 chars) |
|||
# p buf.drop(3) # => 3 (dropped chars) |
|||
# p buf.get(0, 2) # => 'de' (2 chars) |
|||
# p buf.is_eos? # => false (is not EOS here) |
|||
# p buf.drop(5) # => 3 (dropped chars) |
|||
# p buf.is_eos? # => true (is EOS here) |
|||
# p buf[0] # => nil (is EOS here) |
|||
# |
|||
# EXAMPLE 2 -- String. |
|||
# This is a conceptual example. No pros with this. |
|||
# |
|||
# class StrBuf < StreamBuf |
|||
# def initialize(s) |
|||
# @str = s |
|||
# @idx = 0 |
|||
# super() |
|||
# end |
|||
# |
|||
# def read(size) |
|||
# str = @str[@idx, size] |
|||
# @idx += str.size |
|||
# str |
|||
# end |
|||
# end |
|||
# |
|||
class StreamBuf |
|||
# get a char or a partial string from the stream. |
|||
# idx: index of a string to specify a start point of a string to get. |
|||
# unlike String instance, idx < 0 returns nil. |
|||
# n: size of a string to get. |
|||
# returns char at idx if n == nil. |
|||
# returns a partial string, from idx to (idx + n) if n != nil. at EOF, |
|||
# the string size could not equal to arg n. |
|||
def [](idx, n = nil) |
|||
if idx < 0 |
|||
return nil |
|||
end |
|||
if (idx_is_eos?(idx)) |
|||
if n and (@offset + idx == buf_size(@cur_buf)) |
|||
# Like a String, 'abc'[4, 1] returns nil and |
|||
# 'abc'[3, 1] returns '' not nil. |
|||
return '' |
|||
else |
|||
return nil |
|||
end |
|||
end |
|||
my_buf = @cur_buf |
|||
my_offset = @offset |
|||
next_idx = idx |
|||
while (my_offset + next_idx >= buf_size(my_buf)) |
|||
if (my_buf == @buf_tail_idx) |
|||
unless add_buf |
|||
break |
|||
end |
|||
end |
|||
next_idx = my_offset + next_idx - buf_size(my_buf) |
|||
my_buf += 1 |
|||
my_offset = 0 |
|||
end |
|||
loc = my_offset + next_idx |
|||
if !n |
|||
return @buf_list[my_buf][loc] # Fixnum of char code. |
|||
elsif (loc + n - 1 < buf_size(my_buf)) |
|||
return @buf_list[my_buf][loc, n] # String. |
|||
else # should do loop insted of (tail) recursive call... |
|||
res = @buf_list[my_buf][loc, BufSize] |
|||
size_added = buf_size(my_buf) - loc |
|||
if size_added > 0 |
|||
idx += size_added |
|||
n -= size_added |
|||
ret = self[idx, n] |
|||
if ret |
|||
res << ret |
|||
end |
|||
end |
|||
return res |
|||
end |
|||
end |
|||
alias get [] |
|||
|
|||
# drop a string from the stream. |
|||
# returns dropped size. at EOF, dropped size might not equals to arg n. |
|||
# Once you drop the head of the stream, access to the dropped part via [] |
|||
# or get returns nil. |
|||
def drop(n) |
|||
if is_eos? |
|||
return 0 |
|||
end |
|||
size_dropped = 0 |
|||
while (n > 0) |
|||
if !@is_eos or (@cur_buf != @buf_tail_idx) |
|||
if (@offset + n < buf_size(@cur_buf)) |
|||
size_dropped += n |
|||
@offset += n |
|||
n = 0 |
|||
else |
|||
size = buf_size(@cur_buf) - @offset |
|||
size_dropped += size |
|||
n -= size |
|||
@offset = 0 |
|||
unless rel_buf |
|||
unless add_buf |
|||
break |
|||
end |
|||
@cur_buf = @buf_tail_idx |
|||
end |
|||
end |
|||
end |
|||
end |
|||
size_dropped |
|||
end |
|||
|
|||
def is_eos? |
|||
return idx_is_eos?(0) |
|||
end |
|||
|
|||
# WARN: Do not instantiate this class directly. Define your own class |
|||
# which derives this class and define 'read' instance method. |
|||
def initialize |
|||
@buf_list = [] |
|||
@cur_buf = @buf_tail_idx = -1 |
|||
@offset = 0 |
|||
@is_eos = false |
|||
add_buf |
|||
@cur_buf = @buf_tail_idx |
|||
end |
|||
|
|||
protected |
|||
|
|||
def terminate |
|||
while (rel_buf); end |
|||
end |
|||
|
|||
# protected method 'read' must be defined in derived classes. |
|||
# CAUTION: Returning a string which size is not equal to 'size' means |
|||
# EnfOfStream. When it is not at EOS, you must block the callee, try to |
|||
# read and return the sized string. |
|||
def read(size) # raise EOFError |
|||
raise NotImplementedError.new('Method read must be defined in a derived class.') |
|||
end |
|||
|
|||
private |
|||
|
|||
def buf_size(idx) |
|||
@buf_list[idx].size |
|||
end |
|||
|
|||
def add_buf |
|||
if @is_eos |
|||
return false |
|||
end |
|||
begin |
|||
str_read = read(BufSize) |
|||
rescue EOFError |
|||
str_read = nil |
|||
rescue |
|||
terminate |
|||
raise |
|||
end |
|||
if str_read.nil? |
|||
@is_eos = true |
|||
@buf_list.push('') |
|||
@buf_tail_idx += 1 |
|||
false |
|||
else |
|||
@buf_list.push(str_read) |
|||
@buf_tail_idx += 1 |
|||
true |
|||
end |
|||
end |
|||
|
|||
def rel_buf |
|||
if (@cur_buf < 0) |
|||
return false |
|||
end |
|||
@buf_list[@cur_buf] = nil |
|||
if (@cur_buf == @buf_tail_idx) |
|||
@cur_buf = -1 |
|||
return false |
|||
else |
|||
@cur_buf += 1 |
|||
return true |
|||
end |
|||
end |
|||
|
|||
def idx_is_eos?(idx) |
|||
(@is_eos and ((@cur_buf < 0) or (@cur_buf == @buf_tail_idx))) |
|||
end |
|||
|
|||
BufSize = 1024 * 8 |
|||
end |
|||
|
|||
# Buffered IO. |
|||
# |
|||
# EXAMPLE |
|||
# # File 'bigdata' could be a giga-byte size one! |
|||
# buf = CSV::IOBuf.new(File.open('bigdata', 'rb')) |
|||
# CSV::Reader.new(buf).each do |row| |
|||
# p row |
|||
# break if row[0].data == 'admin' |
|||
# end |
|||
# |
|||
class IOBuf < StreamBuf |
|||
def initialize(s) |
|||
@s = s |
|||
super() |
|||
end |
|||
|
|||
def close |
|||
terminate |
|||
end |
|||
|
|||
private |
|||
|
|||
def read(size) |
|||
@s.read(size) |
|||
end |
|||
|
|||
def terminate |
|||
super() |
|||
end |
|||
end |
|||
end |
|||
File diff suppressed because it is too large
File diff suppressed because it is too large
@ -0,0 +1,5 @@ |
|||
# date2 was overridden by date. |
|||
# To be precise, date was overridden by date2, |
|||
# and date2 was renamed to date. |
|||
|
|||
require 'date' |
|||
@ -0,0 +1,947 @@ |
|||
# Copyright (C) 2000 Network Applied Communication Laboratory, Inc. |
|||
# Copyright (C) 2000 Information-technology Promotion Agency, Japan |
|||
# Copyright (C) 2000-2003 NAKAMURA, Hiroshi <nahi@ruby-lang.org> |
|||
|
|||
if $SAFE > 0 |
|||
STDERR.print "-r debug.rb is not available in safe mode\n" |
|||
exit 1 |
|||
end |
|||
|
|||
require 'tracer' |
|||
require 'pp' |
|||
|
|||
class Tracer |
|||
def Tracer.trace_func(*vars) |
|||
Single.trace_func(*vars) |
|||
end |
|||
end |
|||
|
|||
SCRIPT_LINES__ = {} unless defined? SCRIPT_LINES__ |
|||
|
|||
class DEBUGGER__ |
|||
class Mutex |
|||
def initialize |
|||
@locker = nil |
|||
@waiting = [] |
|||
@locked = false; |
|||
end |
|||
|
|||
def locked? |
|||
@locked |
|||
end |
|||
|
|||
def lock |
|||
return if Thread.critical |
|||
return if @locker == Thread.current |
|||
while (Thread.critical = true; @locked) |
|||
@waiting.push Thread.current |
|||
Thread.stop |
|||
end |
|||
@locked = true |
|||
@locker = Thread.current |
|||
Thread.critical = false |
|||
self |
|||
end |
|||
|
|||
def unlock |
|||
return if Thread.critical |
|||
return unless @locked |
|||
unless @locker == Thread.current |
|||
raise RuntimeError, "unlocked by other" |
|||
end |
|||
Thread.critical = true |
|||
t = @waiting.shift |
|||
@locked = false |
|||
@locker = nil |
|||
Thread.critical = false |
|||
t.run if t |
|||
self |
|||
end |
|||
end |
|||
MUTEX = Mutex.new |
|||
|
|||
class Context |
|||
DEBUG_LAST_CMD = [] |
|||
|
|||
begin |
|||
require 'readline' |
|||
def readline(prompt, hist) |
|||
Readline::readline(prompt, hist) |
|||
end |
|||
rescue LoadError |
|||
def readline(prompt, hist) |
|||
STDOUT.print prompt |
|||
STDOUT.flush |
|||
line = STDIN.gets |
|||
exit unless line |
|||
line.chomp! |
|||
line |
|||
end |
|||
USE_READLINE = false |
|||
end |
|||
|
|||
def initialize |
|||
if Thread.current == Thread.main |
|||
@stop_next = 1 |
|||
else |
|||
@stop_next = 0 |
|||
end |
|||
@last_file = nil |
|||
@file = nil |
|||
@line = nil |
|||
@no_step = nil |
|||
@frames = [] |
|||
@finish_pos = 0 |
|||
@trace = false |
|||
@catch = "StandardError" |
|||
@suspend_next = false |
|||
end |
|||
|
|||
def stop_next(n=1) |
|||
@stop_next = n |
|||
end |
|||
|
|||
def set_suspend |
|||
@suspend_next = true |
|||
end |
|||
|
|||
def clear_suspend |
|||
@suspend_next = false |
|||
end |
|||
|
|||
def suspend_all |
|||
DEBUGGER__.suspend |
|||
end |
|||
|
|||
def resume_all |
|||
DEBUGGER__.resume |
|||
end |
|||
|
|||
def check_suspend |
|||
return if Thread.critical |
|||
while (Thread.critical = true; @suspend_next) |
|||
DEBUGGER__.waiting.push Thread.current |
|||
@suspend_next = false |
|||
Thread.stop |
|||
end |
|||
Thread.critical = false |
|||
end |
|||
|
|||
def trace? |
|||
@trace |
|||
end |
|||
|
|||
def set_trace(arg) |
|||
@trace = arg |
|||
end |
|||
|
|||
def stdout |
|||
DEBUGGER__.stdout |
|||
end |
|||
|
|||
def break_points |
|||
DEBUGGER__.break_points |
|||
end |
|||
|
|||
def display |
|||
DEBUGGER__.display |
|||
end |
|||
|
|||
def context(th) |
|||
DEBUGGER__.context(th) |
|||
end |
|||
|
|||
def set_trace_all(arg) |
|||
DEBUGGER__.set_trace(arg) |
|||
end |
|||
|
|||
def set_last_thread(th) |
|||
DEBUGGER__.set_last_thread(th) |
|||
end |
|||
|
|||
def debug_eval(str, binding) |
|||
begin |
|||
val = eval(str, binding) |
|||
rescue StandardError, ScriptError => e |
|||
at = eval("caller(1)", binding) |
|||
stdout.printf "%s:%s\n", at.shift, e.to_s.sub(/\(eval\):1:(in `.*?':)?/, '') |
|||
for i in at |
|||
stdout.printf "\tfrom %s\n", i |
|||
end |
|||
throw :debug_error |
|||
end |
|||
end |
|||
|
|||
def debug_silent_eval(str, binding) |
|||
begin |
|||
eval(str, binding) |
|||
rescue StandardError, ScriptError |
|||
nil |
|||
end |
|||
end |
|||
|
|||
def var_list(ary, binding) |
|||
ary.sort! |
|||
for v in ary |
|||
stdout.printf " %s => %s\n", v, eval(v, binding).inspect |
|||
end |
|||
end |
|||
|
|||
def debug_variable_info(input, binding) |
|||
case input |
|||
when /^\s*g(?:lobal)?\s*$/ |
|||
var_list(global_variables, binding) |
|||
|
|||
when /^\s*l(?:ocal)?\s*$/ |
|||
var_list(eval("local_variables", binding), binding) |
|||
|
|||
when /^\s*i(?:nstance)?\s+/ |
|||
obj = debug_eval($', binding) |
|||
var_list(obj.instance_variables, obj.instance_eval{binding()}) |
|||
|
|||
when /^\s*c(?:onst(?:ant)?)?\s+/ |
|||
obj = debug_eval($', binding) |
|||
unless obj.kind_of? Module |
|||
stdout.print "Should be Class/Module: ", $', "\n" |
|||
else |
|||
var_list(obj.constants, obj.module_eval{binding()}) |
|||
end |
|||
end |
|||
end |
|||
|
|||
def debug_method_info(input, binding) |
|||
case input |
|||
when /^i(:?nstance)?\s+/ |
|||
obj = debug_eval($', binding) |
|||
|
|||
len = 0 |
|||
for v in obj.methods.sort |
|||
len += v.size + 1 |
|||
if len > 70 |
|||
len = v.size + 1 |
|||
stdout.print "\n" |
|||
end |
|||
stdout.print v, " " |
|||
end |
|||
stdout.print "\n" |
|||
|
|||
else |
|||
obj = debug_eval(input, binding) |
|||
unless obj.kind_of? Module |
|||
stdout.print "Should be Class/Module: ", input, "\n" |
|||
else |
|||
len = 0 |
|||
for v in obj.instance_methods(false).sort |
|||
len += v.size + 1 |
|||
if len > 70 |
|||
len = v.size + 1 |
|||
stdout.print "\n" |
|||
end |
|||
stdout.print v, " " |
|||
end |
|||
stdout.print "\n" |
|||
end |
|||
end |
|||
end |
|||
|
|||
def thnum |
|||
num = DEBUGGER__.instance_eval{@thread_list[Thread.current]} |
|||
unless num |
|||
DEBUGGER__.make_thread_list |
|||
num = DEBUGGER__.instance_eval{@thread_list[Thread.current]} |
|||
end |
|||
num |
|||
end |
|||
|
|||
def debug_command(file, line, id, binding) |
|||
MUTEX.lock |
|||
unless defined?($debugger_restart) and $debugger_restart |
|||
callcc{|c| $debugger_restart = c} |
|||
end |
|||
set_last_thread(Thread.current) |
|||
frame_pos = 0 |
|||
binding_file = file |
|||
binding_line = line |
|||
previous_line = nil |
|||
if ENV['EMACS'] |
|||
stdout.printf "\032\032%s:%d:\n", binding_file, binding_line |
|||
else |
|||
stdout.printf "%s:%d:%s", binding_file, binding_line, |
|||
line_at(binding_file, binding_line) |
|||
end |
|||
@frames[0] = [binding, file, line, id] |
|||
display_expressions(binding) |
|||
prompt = true |
|||
while prompt and input = readline("(rdb:%d) "%thnum(), true) |
|||
catch(:debug_error) do |
|||
if input == "" |
|||
next unless DEBUG_LAST_CMD[0] |
|||
input = DEBUG_LAST_CMD[0] |
|||
stdout.print input, "\n" |
|||
else |
|||
DEBUG_LAST_CMD[0] = input |
|||
end |
|||
|
|||
case input |
|||
when /^\s*tr(?:ace)?(?:\s+(on|off))?(?:\s+(all))?$/ |
|||
if defined?( $2 ) |
|||
if $1 == 'on' |
|||
set_trace_all true |
|||
else |
|||
set_trace_all false |
|||
end |
|||
elsif defined?( $1 ) |
|||
if $1 == 'on' |
|||
set_trace true |
|||
else |
|||
set_trace false |
|||
end |
|||
end |
|||
if trace? |
|||
stdout.print "Trace on.\n" |
|||
else |
|||
stdout.print "Trace off.\n" |
|||
end |
|||
|
|||
when /^\s*b(?:reak)?\s+(?:(.+):)?([^.:]+)$/ |
|||
pos = $2 |
|||
if $1 |
|||
klass = debug_silent_eval($1, binding) |
|||
file = $1 |
|||
end |
|||
if pos =~ /^\d+$/ |
|||
pname = pos |
|||
pos = pos.to_i |
|||
else |
|||
pname = pos = pos.intern.id2name |
|||
end |
|||
break_points.push [true, 0, klass || file, pos] |
|||
stdout.printf "Set breakpoint %d at %s:%s\n", break_points.size, klass || file, pname |
|||
|
|||
when /^\s*b(?:reak)?\s+(.+)[#.]([^.:]+)$/ |
|||
pos = $2.intern.id2name |
|||
klass = debug_eval($1, binding) |
|||
break_points.push [true, 0, klass, pos] |
|||
stdout.printf "Set breakpoint %d at %s.%s\n", break_points.size, klass, pos |
|||
|
|||
when /^\s*wat(?:ch)?\s+(.+)$/ |
|||
exp = $1 |
|||
break_points.push [true, 1, exp] |
|||
stdout.printf "Set watchpoint %d:%s\n", break_points.size, exp |
|||
|
|||
when /^\s*b(?:reak)?$/ |
|||
if break_points.find{|b| b[1] == 0} |
|||
n = 1 |
|||
stdout.print "Breakpoints:\n" |
|||
for b in break_points |
|||
if b[0] and b[1] == 0 |
|||
stdout.printf " %d %s:%s\n", n, b[2], b[3] |
|||
end |
|||
n += 1 |
|||
end |
|||
end |
|||
if break_points.find{|b| b[1] == 1} |
|||
n = 1 |
|||
stdout.print "\n" |
|||
stdout.print "Watchpoints:\n" |
|||
for b in break_points |
|||
if b[0] and b[1] == 1 |
|||
stdout.printf " %d %s\n", n, b[2] |
|||
end |
|||
n += 1 |
|||
end |
|||
end |
|||
if break_points.size == 0 |
|||
stdout.print "No breakpoints\n" |
|||
else |
|||
stdout.print "\n" |
|||
end |
|||
|
|||
when /^\s*del(?:ete)?(?:\s+(\d+))?$/ |
|||
pos = $1 |
|||
unless pos |
|||
input = readline("Clear all breakpoints? (y/n) ", false) |
|||
if input == "y" |
|||
for b in break_points |
|||
b[0] = false |
|||
end |
|||
end |
|||
else |
|||
pos = pos.to_i |
|||
if break_points[pos-1] |
|||
break_points[pos-1][0] = false |
|||
else |
|||
stdout.printf "Breakpoint %d is not defined\n", pos |
|||
end |
|||
end |
|||
|
|||
when /^\s*disp(?:lay)?\s+(.+)$/ |
|||
exp = $1 |
|||
display.push [true, exp] |
|||
stdout.printf "%d: ", display.size |
|||
display_expression(exp, binding) |
|||
|
|||
when /^\s*disp(?:lay)?$/ |
|||
display_expressions(binding) |
|||
|
|||
when /^\s*undisp(?:lay)?(?:\s+(\d+))?$/ |
|||
pos = $1 |
|||
unless pos |
|||
input = readline("Clear all expressions? (y/n) ", false) |
|||
if input == "y" |
|||
for d in display |
|||
d[0] = false |
|||
end |
|||
end |
|||
else |
|||
pos = pos.to_i |
|||
if display[pos-1] |
|||
display[pos-1][0] = false |
|||
else |
|||
stdout.printf "Display expression %d is not defined\n", pos |
|||
end |
|||
end |
|||
|
|||
when /^\s*c(?:ont)?$/ |
|||
prompt = false |
|||
|
|||
when /^\s*s(?:tep)?(?:\s+(\d+))?$/ |
|||
if $1 |
|||
lev = $1.to_i |
|||
else |
|||
lev = 1 |
|||
end |
|||
@stop_next = lev |
|||
prompt = false |
|||
|
|||
when /^\s*n(?:ext)?(?:\s+(\d+))?$/ |
|||
if $1 |
|||
lev = $1.to_i |
|||
else |
|||
lev = 1 |
|||
end |
|||
@stop_next = lev |
|||
@no_step = @frames.size - frame_pos |
|||
prompt = false |
|||
|
|||
when /^\s*w(?:here)?$/, /^\s*f(?:rame)?$/ |
|||
display_frames(frame_pos) |
|||
|
|||
when /^\s*l(?:ist)?(?:\s+(.+))?$/ |
|||
if not $1 |
|||
b = previous_line ? previous_line + 10 : binding_line - 5 |
|||
e = b + 9 |
|||
elsif $1 == '-' |
|||
b = previous_line ? previous_line - 10 : binding_line - 5 |
|||
e = b + 9 |
|||
else |
|||
b, e = $1.split(/[-,]/) |
|||
if e |
|||
b = b.to_i |
|||
e = e.to_i |
|||
else |
|||
b = b.to_i - 5 |
|||
e = b + 9 |
|||
end |
|||
end |
|||
previous_line = b |
|||
display_list(b, e, binding_file, binding_line) |
|||
|
|||
when /^\s*up(?:\s+(\d+))?$/ |
|||
previous_line = nil |
|||
if $1 |
|||
lev = $1.to_i |
|||
else |
|||
lev = 1 |
|||
end |
|||
frame_pos += lev |
|||
if frame_pos >= @frames.size |
|||
frame_pos = @frames.size - 1 |
|||
stdout.print "At toplevel\n" |
|||
end |
|||
binding, binding_file, binding_line = @frames[frame_pos] |
|||
stdout.print format_frame(frame_pos) |
|||
|
|||
when /^\s*down(?:\s+(\d+))?$/ |
|||
previous_line = nil |
|||
if $1 |
|||
lev = $1.to_i |
|||
else |
|||
lev = 1 |
|||
end |
|||
frame_pos -= lev |
|||
if frame_pos < 0 |
|||
frame_pos = 0 |
|||
stdout.print "At stack bottom\n" |
|||
end |
|||
binding, binding_file, binding_line = @frames[frame_pos] |
|||
stdout.print format_frame(frame_pos) |
|||
|
|||
when /^\s*fin(?:ish)?$/ |
|||
if frame_pos == @frames.size |
|||
stdout.print "\"finish\" not meaningful in the outermost frame.\n" |
|||
else |
|||
@finish_pos = @frames.size - frame_pos |
|||
frame_pos = 0 |
|||
prompt = false |
|||
end |
|||
|
|||
when /^\s*cat(?:ch)?(?:\s+(.+))?$/ |
|||
if $1 |
|||
excn = $1 |
|||
if excn == 'off' |
|||
@catch = nil |
|||
stdout.print "Clear catchpoint.\n" |
|||
else |
|||
@catch = excn |
|||
stdout.printf "Set catchpoint %s.\n", @catch |
|||
end |
|||
else |
|||
if @catch |
|||
stdout.printf "Catchpoint %s.\n", @catch |
|||
else |
|||
stdout.print "No catchpoint.\n" |
|||
end |
|||
end |
|||
|
|||
when /^\s*q(?:uit)?$/ |
|||
input = readline("Really quit? (y/n) ", false) |
|||
if input == "y" |
|||
exit! # exit -> exit!: No graceful way to stop threads... |
|||
end |
|||
|
|||
when /^\s*v(?:ar)?\s+/ |
|||
debug_variable_info($', binding) |
|||
|
|||
when /^\s*m(?:ethod)?\s+/ |
|||
debug_method_info($', binding) |
|||
|
|||
when /^\s*th(?:read)?\s+/ |
|||
if DEBUGGER__.debug_thread_info($', binding) == :cont |
|||
prompt = false |
|||
end |
|||
|
|||
when /^\s*pp\s+/ |
|||
PP.pp(debug_eval($', binding), stdout) |
|||
|
|||
when /^\s*p\s+/ |
|||
stdout.printf "%s\n", debug_eval($', binding).inspect |
|||
|
|||
when /^\s*r(?:estart)?$/ |
|||
$debugger_restart.call |
|||
|
|||
when /^\s*h(?:elp)?$/ |
|||
debug_print_help() |
|||
|
|||
else |
|||
v = debug_eval(input, binding) |
|||
stdout.printf "%s\n", v.inspect |
|||
end |
|||
end |
|||
end |
|||
MUTEX.unlock |
|||
resume_all |
|||
end |
|||
|
|||
def debug_print_help |
|||
stdout.print <<EOHELP |
|||
Debugger help v.-0.002b |
|||
Commands |
|||
b[reak] [file:|class:]<line|method> |
|||
b[reak] [class.]<line|method> |
|||
set breakpoint to some position |
|||
wat[ch] <expression> set watchpoint to some expression |
|||
cat[ch] (<exception>|off) set catchpoint to an exception |
|||
b[reak] list breakpoints |
|||
cat[ch] show catchpoint |
|||
del[ete][ nnn] delete some or all breakpoints |
|||
disp[lay] <expression> add expression into display expression list |
|||
undisp[lay][ nnn] delete one particular or all display expressions |
|||
c[ont] run until program ends or hit breakpoint |
|||
s[tep][ nnn] step (into methods) one line or till line nnn |
|||
n[ext][ nnn] go over one line or till line nnn |
|||
w[here] display frames |
|||
f[rame] alias for where |
|||
l[ist][ (-|nn-mm)] list program, - lists backwards |
|||
nn-mm lists given lines |
|||
up[ nn] move to higher frame |
|||
down[ nn] move to lower frame |
|||
fin[ish] return to outer frame |
|||
tr[ace] (on|off) set trace mode of current thread |
|||
tr[ace] (on|off) all set trace mode of all threads |
|||
q[uit] exit from debugger |
|||
v[ar] g[lobal] show global variables |
|||
v[ar] l[ocal] show local variables |
|||
v[ar] i[nstance] <object> show instance variables of object |
|||
v[ar] c[onst] <object> show constants of object |
|||
m[ethod] i[nstance] <obj> show methods of object |
|||
m[ethod] <class|module> show instance methods of class or module |
|||
th[read] l[ist] list all threads |
|||
th[read] c[ur[rent]] show current thread |
|||
th[read] [sw[itch]] <nnn> switch thread context to nnn |
|||
th[read] stop <nnn> stop thread nnn |
|||
th[read] resume <nnn> resume thread nnn |
|||
p expression evaluate expression and print its value |
|||
h[elp] print this help |
|||
<everything else> evaluate |
|||
EOHELP |
|||
end |
|||
|
|||
def display_expressions(binding) |
|||
n = 1 |
|||
for d in display |
|||
if d[0] |
|||
stdout.printf "%d: ", n |
|||
display_expression(d[1], binding) |
|||
end |
|||
n += 1 |
|||
end |
|||
end |
|||
|
|||
def display_expression(exp, binding) |
|||
stdout.printf "%s = %s\n", exp, debug_silent_eval(exp, binding).to_s |
|||
end |
|||
|
|||
def frame_set_pos(file, line) |
|||
if @frames[0] |
|||
@frames[0][1] = file |
|||
@frames[0][2] = line |
|||
end |
|||
end |
|||
|
|||
def display_frames(pos) |
|||
0.upto(@frames.size - 1) do |n| |
|||
if n == pos |
|||
stdout.print "--> " |
|||
else |
|||
stdout.print " " |
|||
end |
|||
stdout.print format_frame(n) |
|||
end |
|||
end |
|||
|
|||
def format_frame(pos) |
|||
bind, file, line, id = @frames[pos] |
|||
sprintf "#%d %s:%s%s\n", pos + 1, file, line, |
|||
(id ? ":in `#{id.id2name}'" : "") |
|||
end |
|||
|
|||
def display_list(b, e, file, line) |
|||
stdout.printf "[%d, %d] in %s\n", b, e, file |
|||
if lines = SCRIPT_LINES__[file] and lines != true |
|||
n = 0 |
|||
b.upto(e) do |n| |
|||
if n > 0 && lines[n-1] |
|||
if n == line |
|||
stdout.printf "=> %d %s\n", n, lines[n-1].chomp |
|||
else |
|||
stdout.printf " %d %s\n", n, lines[n-1].chomp |
|||
end |
|||
end |
|||
end |
|||
else |
|||
stdout.printf "No sourcefile available for %s\n", file |
|||
end |
|||
end |
|||
|
|||
def line_at(file, line) |
|||
lines = SCRIPT_LINES__[file] |
|||
if lines |
|||
return "\n" if lines == true |
|||
line = lines[line-1] |
|||
return "\n" unless line |
|||
return line |
|||
end |
|||
return "\n" |
|||
end |
|||
|
|||
def debug_funcname(id) |
|||
if id.nil? |
|||
"toplevel" |
|||
else |
|||
id.id2name |
|||
end |
|||
end |
|||
|
|||
def check_break_points(file, klass, pos, binding, id) |
|||
return false if break_points.empty? |
|||
n = 1 |
|||
for b in break_points |
|||
if b[0] # valid |
|||
if b[1] == 0 # breakpoint |
|||
if (b[2] == file and b[3] == pos) or |
|||
(klass and b[2] == klass and b[3] == pos) |
|||
stdout.printf "Breakpoint %d, %s at %s:%s\n", n, debug_funcname(id), file, pos |
|||
return true |
|||
end |
|||
elsif b[1] == 1 # watchpoint |
|||
if debug_silent_eval(b[2], binding) |
|||
stdout.printf "Watchpoint %d, %s at %s:%s\n", n, debug_funcname(id), file, pos |
|||
return true |
|||
end |
|||
end |
|||
end |
|||
n += 1 |
|||
end |
|||
return false |
|||
end |
|||
|
|||
def excn_handle(file, line, id, binding) |
|||
if $!.class <= SystemExit |
|||
set_trace_func nil |
|||
exit |
|||
end |
|||
|
|||
if @catch and ($!.class.ancestors.find { |e| e.to_s == @catch }) |
|||
stdout.printf "%s:%d: `%s' (%s)\n", file, line, $!, $!.class |
|||
fs = @frames.size |
|||
tb = caller(0)[-fs..-1] |
|||
if tb |
|||
for i in tb |
|||
stdout.printf "\tfrom %s\n", i |
|||
end |
|||
end |
|||
suspend_all |
|||
debug_command(file, line, id, binding) |
|||
end |
|||
end |
|||
|
|||
def trace_func(event, file, line, id, binding, klass) |
|||
Tracer.trace_func(event, file, line, id, binding, klass) if trace? |
|||
context(Thread.current).check_suspend |
|||
@file = file |
|||
@line = line |
|||
case event |
|||
when 'line' |
|||
frame_set_pos(file, line) |
|||
if !@no_step or @frames.size == @no_step |
|||
@stop_next -= 1 |
|||
@stop_next = -1 if @stop_next < 0 |
|||
elsif @frames.size < @no_step |
|||
@stop_next = 0 # break here before leaving... |
|||
else |
|||
# nothing to do. skipped. |
|||
end |
|||
if @stop_next == 0 or check_break_points(file, nil, line, binding, id) |
|||
@no_step = nil |
|||
suspend_all |
|||
debug_command(file, line, id, binding) |
|||
end |
|||
|
|||
when 'call' |
|||
@frames.unshift [binding, file, line, id] |
|||
if check_break_points(file, klass, id.id2name, binding, id) |
|||
suspend_all |
|||
debug_command(file, line, id, binding) |
|||
end |
|||
|
|||
when 'c-call' |
|||
frame_set_pos(file, line) |
|||
|
|||
when 'class' |
|||
@frames.unshift [binding, file, line, id] |
|||
|
|||
when 'return', 'end' |
|||
if @frames.size == @finish_pos |
|||
@stop_next = 1 |
|||
@finish_pos = 0 |
|||
end |
|||
@frames.shift |
|||
|
|||
when 'end' |
|||
@frames.shift |
|||
|
|||
when 'raise' |
|||
excn_handle(file, line, id, binding) |
|||
|
|||
end |
|||
@last_file = file |
|||
end |
|||
end |
|||
|
|||
trap("INT") { DEBUGGER__.interrupt } |
|||
@last_thread = Thread::main |
|||
@max_thread = 1 |
|||
@thread_list = {Thread::main => 1} |
|||
@break_points = [] |
|||
@display = [] |
|||
@waiting = [] |
|||
@stdout = STDOUT |
|||
|
|||
class << DEBUGGER__ |
|||
def stdout |
|||
@stdout |
|||
end |
|||
|
|||
def stdout=(s) |
|||
@stdout = s |
|||
end |
|||
|
|||
def display |
|||
@display |
|||
end |
|||
|
|||
def break_points |
|||
@break_points |
|||
end |
|||
|
|||
def waiting |
|||
@waiting |
|||
end |
|||
|
|||
def set_trace( arg ) |
|||
saved_crit = Thread.critical |
|||
Thread.critical = true |
|||
make_thread_list |
|||
for th, in @thread_list |
|||
context(th).set_trace arg |
|||
end |
|||
Thread.critical = saved_crit |
|||
arg |
|||
end |
|||
|
|||
def set_last_thread(th) |
|||
@last_thread = th |
|||
end |
|||
|
|||
def suspend |
|||
saved_crit = Thread.critical |
|||
Thread.critical = true |
|||
make_thread_list |
|||
for th, in @thread_list |
|||
next if th == Thread.current |
|||
context(th).set_suspend |
|||
end |
|||
Thread.critical = saved_crit |
|||
# Schedule other threads to suspend as soon as possible. |
|||
Thread.pass unless Thread.critical |
|||
end |
|||
|
|||
def resume |
|||
saved_crit = Thread.critical |
|||
Thread.critical = true |
|||
make_thread_list |
|||
for th, in @thread_list |
|||
next if th == Thread.current |
|||
context(th).clear_suspend |
|||
end |
|||
waiting.each do |th| |
|||
th.run |
|||
end |
|||
waiting.clear |
|||
Thread.critical = saved_crit |
|||
# Schedule other threads to restart as soon as possible. |
|||
Thread.pass |
|||
end |
|||
|
|||
def context(thread=Thread.current) |
|||
c = thread[:__debugger_data__] |
|||
unless c |
|||
thread[:__debugger_data__] = c = Context.new |
|||
end |
|||
c |
|||
end |
|||
|
|||
def interrupt |
|||
context(@last_thread).stop_next |
|||
end |
|||
|
|||
def get_thread(num) |
|||
th = @thread_list.index(num) |
|||
unless th |
|||
@stdout.print "No thread ##{num}\n" |
|||
throw :debug_error |
|||
end |
|||
th |
|||
end |
|||
|
|||
def thread_list(num) |
|||
th = get_thread(num) |
|||
if th == Thread.current |
|||
@stdout.print "+" |
|||
else |
|||
@stdout.print " " |
|||
end |
|||
@stdout.printf "%d ", num |
|||
@stdout.print th.inspect, "\t" |
|||
file = context(th).instance_eval{@file} |
|||
if file |
|||
@stdout.print file,":",context(th).instance_eval{@line} |
|||
end |
|||
@stdout.print "\n" |
|||
end |
|||
|
|||
def thread_list_all |
|||
for th in @thread_list.values.sort |
|||
thread_list(th) |
|||
end |
|||
end |
|||
|
|||
def make_thread_list |
|||
hash = {} |
|||
for th in Thread::list |
|||
if @thread_list.key? th |
|||
hash[th] = @thread_list[th] |
|||
else |
|||
@max_thread += 1 |
|||
hash[th] = @max_thread |
|||
end |
|||
end |
|||
@thread_list = hash |
|||
end |
|||
|
|||
def debug_thread_info(input, binding) |
|||
case input |
|||
when /^l(?:ist)?/ |
|||
make_thread_list |
|||
thread_list_all |
|||
|
|||
when /^c(?:ur(?:rent)?)?$/ |
|||
make_thread_list |
|||
thread_list(@thread_list[Thread.current]) |
|||
|
|||
when /^(?:sw(?:itch)?\s+)?(\d+)/ |
|||
make_thread_list |
|||
th = get_thread($1.to_i) |
|||
if th == Thread.current |
|||
@stdout.print "It's the current thread.\n" |
|||
else |
|||
thread_list(@thread_list[th]) |
|||
context(th).stop_next |
|||
th.run |
|||
return :cont |
|||
end |
|||
|
|||
when /^stop\s+(\d+)/ |
|||
make_thread_list |
|||
th = get_thread($1.to_i) |
|||
if th == Thread.current |
|||
@stdout.print "It's the current thread.\n" |
|||
elsif th.stop? |
|||
@stdout.print "Already stopped.\n" |
|||
else |
|||
thread_list(@thread_list[th]) |
|||
context(th).suspend |
|||
end |
|||
|
|||
when /^resume\s+(\d+)/ |
|||
make_thread_list |
|||
th = get_thread($1.to_i) |
|||
if th == Thread.current |
|||
@stdout.print "It's the current thread.\n" |
|||
elsif !th.stop? |
|||
@stdout.print "Already running." |
|||
else |
|||
thread_list(@thread_list[th]) |
|||
th.run |
|||
end |
|||
end |
|||
end |
|||
end |
|||
|
|||
stdout.printf "Debug.rb\n" |
|||
stdout.printf "Emacs support available.\n\n" |
|||
set_trace_func proc { |event, file, line, id, binding, klass, *rest| |
|||
DEBUGGER__.context.trace_func event, file, line, id, binding, klass |
|||
} |
|||
end |
|||
@ -0,0 +1,339 @@ |
|||
# = delegate -- Support for the Delegation Pattern |
|||
# |
|||
# Documentation by James Edward Gray II and Gavin Sinclair |
|||
# |
|||
# == Introduction |
|||
# |
|||
# This library provides three different ways to delegate method calls to an |
|||
# object. The easiest to use is SimpleDelegator. Pass an object to the |
|||
# constructor and all methods supported by the object will be delegated. This |
|||
# object can be changed later. |
|||
# |
|||
# Going a step further, the top level DelegateClass method allows you to easily |
|||
# setup delegation through class inheritance. This is considerably more |
|||
# flexible and thus probably the most common use for this library. |
|||
# |
|||
# Finally, if you need full control over the delegation scheme, you can inherit |
|||
# from the abstract class Delegator and customize as needed. (If you find |
|||
# yourself needing this control, have a look at _forwardable_, also in the |
|||
# standard library. It may suit your needs better.) |
|||
# |
|||
# == Notes |
|||
# |
|||
# Be advised, RDoc will not detect delegated methods. |
|||
# |
|||
# <b>delegate.rb provides full-class delegation via the |
|||
# DelegateClass() method. For single-method delegation via |
|||
# def_delegator(), see forwardable.rb.</b> |
|||
# |
|||
# == Examples |
|||
# |
|||
# === SimpleDelegator |
|||
# |
|||
# Here's a simple example that takes advantage of the fact that |
|||
# SimpleDelegator's delegation object can be changed at any time. |
|||
# |
|||
# class Stats |
|||
# def initialize |
|||
# @source = SimpleDelegator.new([]) |
|||
# end |
|||
# |
|||
# def stats( records ) |
|||
# @source.__setobj__(records) |
|||
# |
|||
# "Elements: #{@source.size}\n" + |
|||
# " Non-Nil: #{@source.compact.size}\n" + |
|||
# " Unique: #{@source.uniq.size}\n" |
|||
# end |
|||
# end |
|||
# |
|||
# s = Stats.new |
|||
# puts s.stats(%w{James Edward Gray II}) |
|||
# puts |
|||
# puts s.stats([1, 2, 3, nil, 4, 5, 1, 2]) |
|||
# |
|||
# <i>Prints:</i> |
|||
# |
|||
# Elements: 4 |
|||
# Non-Nil: 4 |
|||
# Unique: 4 |
|||
# |
|||
# Elements: 8 |
|||
# Non-Nil: 7 |
|||
# Unique: 6 |
|||
# |
|||
# === DelegateClass() |
|||
# |
|||
# Here's a sample of use from <i>tempfile.rb</i>. |
|||
# |
|||
# A _Tempfile_ object is really just a _File_ object with a few special rules |
|||
# about storage location and/or when the File should be deleted. That makes for |
|||
# an almost textbook perfect example of how to use delegation. |
|||
# |
|||
# class Tempfile < DelegateClass(File) |
|||
# # constant and class member data initialization... |
|||
# |
|||
# def initialize(basename, tmpdir=Dir::tmpdir) |
|||
# # build up file path/name in var tmpname... |
|||
# |
|||
# @tmpfile = File.open(tmpname, File::RDWR|File::CREAT|File::EXCL, 0600) |
|||
# |
|||
# # ... |
|||
# |
|||
# super(@tmpfile) |
|||
# |
|||
# # below this point, all methods of File are supported... |
|||
# end |
|||
# |
|||
# # ... |
|||
# end |
|||
# |
|||
# === Delegator |
|||
# |
|||
# SimpleDelegator's implementation serves as a nice example here. |
|||
# |
|||
# class SimpleDelegator < Delegator |
|||
# def initialize(obj) |
|||
# super # pass obj to Delegator constructor, required |
|||
# @_sd_obj = obj # store obj for future use |
|||
# end |
|||
# |
|||
# def __getobj__ |
|||
# @_sd_obj # return object we are delegating to, required |
|||
# end |
|||
# |
|||
# def __setobj__(obj) |
|||
# @_sd_obj = obj # change delegation object, a feature we're providing |
|||
# end |
|||
# |
|||
# # ... |
|||
# end |
|||
|
|||
# |
|||
# Delegator is an abstract class used to build delegator pattern objects from |
|||
# subclasses. Subclasses should redefine \_\_getobj\_\_. For a concrete |
|||
# implementation, see SimpleDelegator. |
|||
# |
|||
class Delegator |
|||
|
|||
# |
|||
# Pass in the _obj_ to delegate method calls to. All methods supported by |
|||
# _obj_ will be delegated to. |
|||
# |
|||
def initialize(obj) |
|||
preserved = ::Kernel.public_instance_methods(false) |
|||
preserved -= ["to_s","to_a","inspect","==","=~","==="] |
|||
for t in self.class.ancestors |
|||
preserved |= t.public_instance_methods(false) |
|||
preserved |= t.private_instance_methods(false) |
|||
preserved |= t.protected_instance_methods(false) |
|||
break if t == Delegator |
|||
end |
|||
preserved << "singleton_method_added" |
|||
for method in obj.methods |
|||
next if preserved.include? method |
|||
begin |
|||
eval <<-EOS |
|||
def self.#{method}(*args, &block) |
|||
begin |
|||
__getobj__.__send__(:#{method}, *args, &block) |
|||
rescue Exception |
|||
$@.delete_if{|s| /:in `__getobj__'$/ =~ s} #` |
|||
$@.delete_if{|s| /^\\(eval\\):/ =~ s} |
|||
Kernel::raise |
|||
end |
|||
end |
|||
EOS |
|||
rescue SyntaxError |
|||
raise NameError, "invalid identifier %s" % method, caller(4) |
|||
end |
|||
end |
|||
end |
|||
alias initialize_methods initialize |
|||
|
|||
# Handles the magic of delegation through \_\_getobj\_\_. |
|||
def method_missing(m, *args) |
|||
target = self.__getobj__ |
|||
unless target.respond_to?(m) |
|||
super(m, *args) |
|||
end |
|||
target.__send__(m, *args) |
|||
end |
|||
|
|||
# |
|||
# Checks for a method provided by this the delegate object by fowarding the |
|||
# call through \_\_getobj\_\_. |
|||
# |
|||
def respond_to?(m, include_private = false) |
|||
return true if super |
|||
return self.__getobj__.respond_to?(m, include_private) |
|||
end |
|||
|
|||
# |
|||
# This method must be overridden by subclasses and should return the object |
|||
# method calls are being delegated to. |
|||
# |
|||
def __getobj__ |
|||
raise NotImplementedError, "need to define `__getobj__'" |
|||
end |
|||
|
|||
# Serialization support for the object returned by \_\_getobj\_\_. |
|||
def marshal_dump |
|||
__getobj__ |
|||
end |
|||
# Reinitializes delegation from a serialized object. |
|||
def marshal_load(obj) |
|||
initialize_methods(obj) |
|||
__setobj__(obj) |
|||
end |
|||
end |
|||
|
|||
# |
|||
# A concrete implementation of Delegator, this class provides the means to |
|||
# delegate all supported method calls to the object passed into the constructor |
|||
# and even to change the object being delegated to at a later time with |
|||
# \_\_setobj\_\_ . |
|||
# |
|||
class SimpleDelegator<Delegator |
|||
|
|||
# Pass in the _obj_ you would like to delegate method calls to. |
|||
def initialize(obj) |
|||
super |
|||
@_sd_obj = obj |
|||
end |
|||
|
|||
# Returns the current object method calls are being delegated to. |
|||
def __getobj__ |
|||
@_sd_obj |
|||
end |
|||
|
|||
# |
|||
# Changes the delegate object to _obj_. |
|||
# |
|||
# It's important to note that this does *not* cause SimpleDelegator's methods |
|||
# to change. Because of this, you probably only want to change delegation |
|||
# to objects of the same type as the original delegate. |
|||
# |
|||
# Here's an example of changing the delegation object. |
|||
# |
|||
# names = SimpleDelegator.new(%w{James Edward Gray II}) |
|||
# puts names[1] # => Edward |
|||
# names.__setobj__(%w{Gavin Sinclair}) |
|||
# puts names[1] # => Sinclair |
|||
# |
|||
def __setobj__(obj) |
|||
raise ArgumentError, "cannot delegate to self" if self.equal?(obj) |
|||
@_sd_obj = obj |
|||
end |
|||
|
|||
# Clone support for the object returned by \_\_getobj\_\_. |
|||
def clone |
|||
new = super |
|||
new.__setobj__(__getobj__.clone) |
|||
new |
|||
end |
|||
# Duplication support for the object returned by \_\_getobj\_\_. |
|||
def dup |
|||
new = super |
|||
new.__setobj__(__getobj__.clone) |
|||
new |
|||
end |
|||
end |
|||
|
|||
# :stopdoc: |
|||
# backward compatibility ^_^;;; |
|||
Delegater = Delegator |
|||
SimpleDelegater = SimpleDelegator |
|||
# :startdoc: |
|||
|
|||
# |
|||
# The primary interface to this library. Use to setup delegation when defining |
|||
# your class. |
|||
# |
|||
# class MyClass < DelegateClass( ClassToDelegateTo ) # Step 1 |
|||
# def initiaize |
|||
# super(obj_of_ClassToDelegateTo) # Step 2 |
|||
# end |
|||
# end |
|||
# |
|||
def DelegateClass(superclass) |
|||
klass = Class.new |
|||
methods = superclass.public_instance_methods(true) |
|||
methods -= ::Kernel.public_instance_methods(false) |
|||
methods |= ["to_s","to_a","inspect","==","=~","==="] |
|||
klass.module_eval { |
|||
def initialize(obj) # :nodoc: |
|||
@_dc_obj = obj |
|||
end |
|||
def method_missing(m, *args) # :nodoc: |
|||
unless @_dc_obj.respond_to?(m) |
|||
super(m, *args) |
|||
end |
|||
@_dc_obj.__send__(m, *args) |
|||
end |
|||
def respond_to?(m, include_private = false) # :nodoc: |
|||
return true if super |
|||
return @_dc_obj.respond_to?(m, include_private) |
|||
end |
|||
def __getobj__ # :nodoc: |
|||
@_dc_obj |
|||
end |
|||
def __setobj__(obj) # :nodoc: |
|||
raise ArgumentError, "cannot delegate to self" if self.equal?(obj) |
|||
@_dc_obj = obj |
|||
end |
|||
def clone # :nodoc: |
|||
new = super |
|||
new.__setobj__(__getobj__.clone) |
|||
new |
|||
end |
|||
def dup # :nodoc: |
|||
new = super |
|||
new.__setobj__(__getobj__.clone) |
|||
new |
|||
end |
|||
} |
|||
for method in methods |
|||
begin |
|||
klass.module_eval <<-EOS |
|||
def #{method}(*args, &block) |
|||
begin |
|||
@_dc_obj.__send__(:#{method}, *args, &block) |
|||
rescue |
|||
$@[0,2] = nil |
|||
raise |
|||
end |
|||
end |
|||
EOS |
|||
rescue SyntaxError |
|||
raise NameError, "invalid identifier %s" % method, caller(3) |
|||
end |
|||
end |
|||
return klass |
|||
end |
|||
|
|||
# :enddoc: |
|||
|
|||
if __FILE__ == $0 |
|||
class ExtArray<DelegateClass(Array) |
|||
def initialize() |
|||
super([]) |
|||
end |
|||
end |
|||
|
|||
ary = ExtArray.new |
|||
p ary.class |
|||
ary.push 25 |
|||
p ary |
|||
|
|||
foo = Object.new |
|||
def foo.test |
|||
25 |
|||
end |
|||
def foo.error |
|||
raise 'this is OK' |
|||
end |
|||
foo2 = SimpleDelegator.new(foo) |
|||
p foo.test == foo2.test # => true |
|||
foo2.error # raise error! |
|||
end |
|||
@ -0,0 +1,50 @@ |
|||
require 'digest.so' |
|||
|
|||
module Digest |
|||
def self.const_missing(name) |
|||
case name |
|||
when :SHA256, :SHA384, :SHA512 |
|||
lib = 'digest/sha2.so' |
|||
else |
|||
lib = File.join('digest', name.to_s.downcase) |
|||
end |
|||
|
|||
begin |
|||
require lib |
|||
rescue LoadError => e |
|||
raise LoadError, "library not found for class Digest::#{name} -- #{lib}", caller(1) |
|||
end |
|||
unless Digest.const_defined?(name) |
|||
raise NameError, "uninitialized constant Digest::#{name}", caller(1) |
|||
end |
|||
Digest.const_get(name) |
|||
end |
|||
|
|||
class ::Digest::Class |
|||
# creates a digest object and reads a given file, _name_. |
|||
# |
|||
# p Digest::SHA256.file("X11R6.8.2-src.tar.bz2").hexdigest |
|||
# # => "f02e3c85572dc9ad7cb77c2a638e3be24cc1b5bea9fdbb0b0299c9668475c534" |
|||
def self.file(name) |
|||
new.file(name) |
|||
end |
|||
end |
|||
|
|||
module Instance |
|||
# updates the digest with the contents of a given file _name_ and |
|||
# returns self. |
|||
def file(name) |
|||
File.open(name, "rb") {|f| |
|||
buf = "" |
|||
while f.read(16384, buf) |
|||
update buf |
|||
end |
|||
} |
|||
self |
|||
end |
|||
end |
|||
end |
|||
|
|||
def Digest(name) |
|||
Digest.const_get(name) |
|||
end |
|||
@ -0,0 +1,73 @@ |
|||
#-- |
|||
# sha2.rb - defines Digest::SHA2 class which wraps up the SHA256, |
|||
# SHA384, and SHA512 classes. |
|||
#++ |
|||
# Copyright (c) 2006 Akinori MUSHA <knu@iDaemons.org> |
|||
# |
|||
# All rights reserved. You can redistribute and/or modify it under the same |
|||
# terms as Ruby. |
|||
# |
|||
# $Id: sha2.rb 11708 2007-02-12 23:01:19Z shyouhei $ |
|||
|
|||
require 'digest' |
|||
|
|||
module Digest |
|||
# |
|||
# A meta digest provider class for SHA256, SHA384 and SHA512. |
|||
# |
|||
class SHA2 < Digest::Class |
|||
# call-seq: |
|||
# Digest::SHA2.new(bitlen = 256) -> digest_obj |
|||
# |
|||
# Creates a new SHA2 hash object with a given bit length. |
|||
def initialize(bitlen = 256) |
|||
case bitlen |
|||
when 256 |
|||
@sha2 = Digest::SHA256.new |
|||
when 384 |
|||
@sha2 = Digest::SHA384.new |
|||
when 512 |
|||
@sha2 = Digest::SHA512.new |
|||
else |
|||
raise ArgumentError, "unsupported bit length: %s" % bitlen.inspect |
|||
end |
|||
@bitlen = bitlen |
|||
end |
|||
|
|||
# :nodoc: |
|||
def reset |
|||
@sha2.reset |
|||
self |
|||
end |
|||
|
|||
# :nodoc: |
|||
def update(str) |
|||
@sha2.update(str) |
|||
self |
|||
end |
|||
alias << update |
|||
|
|||
def finish |
|||
@sha2.digest! |
|||
end |
|||
private :finish |
|||
|
|||
def block_length |
|||
@sha2.block_length |
|||
end |
|||
|
|||
def digest_length |
|||
@sha2.digest_length |
|||
end |
|||
|
|||
# :nodoc: |
|||
def initialize_copy(other) |
|||
@sha2 = other.instance_eval { @sha2.clone } |
|||
end |
|||
|
|||
# :nodoc: |
|||
def inspect |
|||
"#<%s:%d %s>" % [self.class.name, @bitlen, hexdigest] |
|||
end |
|||
end |
|||
end |
|||
@ -0,0 +1,225 @@ |
|||
# -*- ruby -*- |
|||
|
|||
require 'dl' |
|||
require 'dl/types' |
|||
|
|||
module DL |
|||
module Importable |
|||
LIB_MAP = {} |
|||
|
|||
module Internal |
|||
def init_types() |
|||
@types ||= ::DL::Types.new |
|||
end |
|||
|
|||
def init_sym() |
|||
@SYM ||= {} |
|||
end |
|||
|
|||
def [](name) |
|||
return @SYM[name.to_s][0] |
|||
end |
|||
|
|||
def dlload(*libnames) |
|||
if( !defined?(@LIBS) ) |
|||
@LIBS = [] |
|||
end |
|||
libnames.each{|libname| |
|||
if( !LIB_MAP[libname] ) |
|||
LIB_MAP[libname] = DL.dlopen(libname) |
|||
end |
|||
@LIBS.push(LIB_MAP[libname]) |
|||
} |
|||
end |
|||
alias dllink :dlload |
|||
|
|||
def parse_cproto(proto) |
|||
proto = proto.gsub(/\s+/, " ").strip |
|||
case proto |
|||
when /^([\d\w\*_\s]+)\(([\d\w\*_\s\,\[\]]*)\)$/ |
|||
ret = $1 |
|||
args = $2.strip() |
|||
ret = ret.split(/\s+/) |
|||
args = args.split(/\s*,\s*/) |
|||
func = ret.pop() |
|||
if( func =~ /^\*/ ) |
|||
func.gsub!(/^\*+/,"") |
|||
ret.push("*") |
|||
end |
|||
ret = ret.join(" ") |
|||
return [func, ret, args] |
|||
else |
|||
raise(RuntimeError,"can't parse the function prototype: #{proto}") |
|||
end |
|||
end |
|||
|
|||
# example: |
|||
# extern "int strlen(char*)" |
|||
# |
|||
def extern(proto) |
|||
func,ret,args = parse_cproto(proto) |
|||
return import(func, ret, args) |
|||
end |
|||
|
|||
# example: |
|||
# callback "int method_name(int, char*)" |
|||
# |
|||
def callback(proto) |
|||
func,ret,args = parse_cproto(proto) |
|||
|
|||
init_types() |
|||
init_sym() |
|||
|
|||
rty,renc,rdec = @types.encode_return_type(ret) |
|||
if( !rty ) |
|||
raise(TypeError, "unsupported type: #{ret}") |
|||
end |
|||
ty,enc,dec = encode_argument_types(args) |
|||
symty = rty + ty |
|||
|
|||
module_eval("module_function :#{func}") |
|||
sym = module_eval([ |
|||
"DL::callback(\"#{symty}\"){|*args|", |
|||
" sym,rdec,enc,dec = @SYM['#{func}']", |
|||
" args = enc.call(args) if enc", |
|||
" r,rs = #{func}(*args)", |
|||
" r = renc.call(r) if rdec", |
|||
" rs = dec.call(rs) if (dec && rs)", |
|||
" @retval = r", |
|||
" @args = rs", |
|||
" r", |
|||
"}", |
|||
].join("\n")) |
|||
|
|||
@SYM[func] = [sym,rdec,enc,dec] |
|||
|
|||
return sym |
|||
end |
|||
|
|||
# example: |
|||
# typealias("uint", "unsigned int") |
|||
# |
|||
def typealias(alias_type, ty1, enc1=nil, dec1=nil, ty2=nil, enc2=nil, dec2=nil) |
|||
init_types() |
|||
@types.typealias(alias_type, ty1, enc1, dec1, |
|||
ty2||ty1, enc2, dec2) |
|||
end |
|||
|
|||
# example: |
|||
# symbol "foo_value" |
|||
# symbol "foo_func", "IIP" |
|||
# |
|||
def symbol(name, ty = nil) |
|||
sym = nil |
|||
@LIBS.each{|lib| |
|||
begin |
|||
if( ty ) |
|||
sym = lib[name, ty] |
|||
else |
|||
sym = lib[name] |
|||
end |
|||
rescue |
|||
next |
|||
end |
|||
} |
|||
if( !sym ) |
|||
raise(RuntimeError, "can't find the symbol `#{name}'") |
|||
end |
|||
return sym |
|||
end |
|||
|
|||
# example: |
|||
# import("get_length", "int", ["void*", "int"]) |
|||
# |
|||
def import(name, rettype, argtypes = nil) |
|||
init_types() |
|||
init_sym() |
|||
|
|||
rty,_,rdec = @types.encode_return_type(rettype) |
|||
if( !rty ) |
|||
raise(TypeError, "unsupported type: #{rettype}") |
|||
end |
|||
ty,enc,dec = encode_argument_types(argtypes) |
|||
symty = rty + ty |
|||
|
|||
sym = symbol(name, symty) |
|||
|
|||
mname = name.dup |
|||
if( ?A <= mname[0] && mname[0] <= ?Z ) |
|||
mname[0,1] = mname[0,1].downcase |
|||
end |
|||
@SYM[mname] = [sym,rdec,enc,dec] |
|||
|
|||
module_eval [ |
|||
"def #{mname}(*args)", |
|||
" sym,rdec,enc,dec = @SYM['#{mname}']", |
|||
" args = enc.call(args) if enc", |
|||
if( $DEBUG ) |
|||
" p \"[DL] call #{mname} with \#{args.inspect}\"" |
|||
else |
|||
"" |
|||
end, |
|||
" r,rs = sym.call(*args)", |
|||
if( $DEBUG ) |
|||
" p \"[DL] retval=\#{r.inspect} args=\#{rs.inspect}\"" |
|||
else |
|||
"" |
|||
end, |
|||
" r = rdec.call(r) if rdec", |
|||
" rs = dec.call(rs) if dec", |
|||
" @retval = r", |
|||
" @args = rs", |
|||
" return r", |
|||
"end", |
|||
"module_function :#{mname}", |
|||
].join("\n") |
|||
|
|||
return sym |
|||
end |
|||
|
|||
def _args_ |
|||
return @args |
|||
end |
|||
|
|||
def _retval_ |
|||
return @retval |
|||
end |
|||
|
|||
def encode_argument_types(tys) |
|||
init_types() |
|||
encty = [] |
|||
enc = nil |
|||
dec = nil |
|||
tys.each_with_index{|ty,idx| |
|||
ty,c1,c2 = @types.encode_argument_type(ty) |
|||
if( !ty ) |
|||
raise(TypeError, "unsupported type: #{ty}") |
|||
end |
|||
encty.push(ty) |
|||
if( enc ) |
|||
if( c1 ) |
|||
conv1 = enc |
|||
enc = proc{|v| v = conv1.call(v); v[idx] = c1.call(v[idx]); v} |
|||
end |
|||
else |
|||
if( c1 ) |
|||
enc = proc{|v| v[idx] = c1.call(v[idx]); v} |
|||
end |
|||
end |
|||
if( dec ) |
|||
if( c2 ) |
|||
conv2 = dec |
|||
dec = proc{|v| v = conv2.call(v); v[idx] = c2.call(v[idx]); v} |
|||
end |
|||
else |
|||
if( c2 ) |
|||
dec = proc{|v| v[idx] = c2.call(v[idx]); v} |
|||
end |
|||
end |
|||
} |
|||
return [encty.join, enc, dec] |
|||
end |
|||
end # end of Internal |
|||
include Internal |
|||
end # end of Importable |
|||
end |
|||
@ -0,0 +1,149 @@ |
|||
# -*- ruby -*- |
|||
|
|||
require 'dl' |
|||
require 'dl/import' |
|||
|
|||
module DL |
|||
module Importable |
|||
module Internal |
|||
def define_struct(contents) |
|||
init_types() |
|||
Struct.new(@types, contents) |
|||
end |
|||
alias struct define_struct |
|||
|
|||
def define_union(contents) |
|||
init_types() |
|||
Union.new(@types, contents) |
|||
end |
|||
alias union define_union |
|||
|
|||
class Memory |
|||
def initialize(ptr, names, ty, len, enc, dec) |
|||
@ptr = ptr |
|||
@names = names |
|||
@ty = ty |
|||
@len = len |
|||
@enc = enc |
|||
@dec = dec |
|||
|
|||
# define methods |
|||
@names.each{|name| |
|||
instance_eval [ |
|||
"def #{name}", |
|||
" v = @ptr[\"#{name}\"]", |
|||
" if( @len[\"#{name}\"] )", |
|||
" v = v.collect{|x| @dec[\"#{name}\"] ? @dec[\"#{name}\"].call(x) : x }", |
|||
" else", |
|||
" v = @dec[\"#{name}\"].call(v) if @dec[\"#{name}\"]", |
|||
" end", |
|||
" return v", |
|||
"end", |
|||
"def #{name}=(v)", |
|||
" if( @len[\"#{name}\"] )", |
|||
" v = v.collect{|x| @enc[\"#{name}\"] ? @enc[\"#{name}\"].call(x) : x }", |
|||
" else", |
|||
" v = @enc[\"#{name}\"].call(v) if @enc[\"#{name}\"]", |
|||
" end", |
|||
" @ptr[\"#{name}\"] = v", |
|||
" return v", |
|||
"end", |
|||
].join("\n") |
|||
} |
|||
end |
|||
|
|||
def to_ptr |
|||
return @ptr |
|||
end |
|||
|
|||
def size |
|||
return @ptr.size |
|||
end |
|||
end |
|||
|
|||
class Struct |
|||
def initialize(types, contents) |
|||
@names = [] |
|||
@ty = {} |
|||
@len = {} |
|||
@enc = {} |
|||
@dec = {} |
|||
@size = 0 |
|||
@tys = "" |
|||
@types = types |
|||
parse(contents) |
|||
end |
|||
|
|||
def size |
|||
return @size |
|||
end |
|||
|
|||
def members |
|||
return @names |
|||
end |
|||
|
|||
# ptr must be a PtrData object. |
|||
def new(ptr) |
|||
ptr.struct!(@tys, *@names) |
|||
mem = Memory.new(ptr, @names, @ty, @len, @enc, @dec) |
|||
return mem |
|||
end |
|||
|
|||
def malloc(size = nil) |
|||
if( !size ) |
|||
size = @size |
|||
end |
|||
ptr = DL::malloc(size) |
|||
return new(ptr) |
|||
end |
|||
|
|||
def parse(contents) |
|||
contents.each{|elem| |
|||
name,ty,num,enc,dec = parse_elem(elem) |
|||
@names.push(name) |
|||
@ty[name] = ty |
|||
@len[name] = num |
|||
@enc[name] = enc |
|||
@dec[name] = dec |
|||
if( num ) |
|||
@tys += "#{ty}#{num}" |
|||
else |
|||
@tys += ty |
|||
end |
|||
} |
|||
@size = DL.sizeof(@tys) |
|||
end |
|||
|
|||
def parse_elem(elem) |
|||
elem.strip! |
|||
case elem |
|||
when /^([\w\d_\*]+)([\*\s]+)([\w\d_]+)$/ |
|||
ty = ($1 + $2).strip |
|||
name = $3 |
|||
num = nil; |
|||
when /^([\w\d_\*]+)([\*\s]+)([\w\d_]+)\[(\d+)\]$/ |
|||
ty = ($1 + $2).strip |
|||
name = $3 |
|||
num = $4.to_i |
|||
else |
|||
raise(RuntimeError, "invalid element: #{elem}") |
|||
end |
|||
ty,enc,dec = @types.encode_struct_type(ty) |
|||
if( !ty ) |
|||
raise(TypeError, "unsupported type: #{ty}") |
|||
end |
|||
return [name,ty,num,enc,dec] |
|||
end |
|||
end # class Struct |
|||
|
|||
class Union < Struct |
|||
def new |
|||
ptr = DL::malloc(@size) |
|||
ptr.union!(@tys, *@names) |
|||
mem = Memory.new(ptr, @names, @ty, @len, @enc, @dec) |
|||
return mem |
|||
end |
|||
end |
|||
end # module Internal |
|||
end # module Importable |
|||
end # module DL |
|||
@ -0,0 +1,245 @@ |
|||
# -*- ruby -*- |
|||
|
|||
require 'dl' |
|||
|
|||
module DL |
|||
class Types |
|||
TYPES = [ |
|||
# FORMAT: |
|||
# ["alias name", |
|||
# "type name", encoding_method, decoding_method, for function prototypes |
|||
# "type name", encoding_method, decoding_method] for structures (not implemented) |
|||
|
|||
# for Windows |
|||
["DWORD", "unsigned long", nil, nil, |
|||
"unsigned long", nil, nil], |
|||
["PDWORD", "unsigned long *", nil, nil, |
|||
"unsigned long *", nil, nil], |
|||
["WORD", "unsigned short", nil, nil, |
|||
"unsigned short", nil, nil], |
|||
["PWORD", "unsigned int *", nil, nil, |
|||
"unsigned int *", nil, nil], |
|||
["BYTE", "unsigned char", nil, nil, |
|||
"unsigned char", nil, nil], |
|||
["PBYTE", "unsigned char *", nil, nil, |
|||
"unsigned char *", nil, nil], |
|||
["BOOL", "ibool", nil, nil, |
|||
"ibool", nil, nil], |
|||
["ATOM", "int", nil, nil, |
|||
"int", nil, nil], |
|||
["BYTE", "unsigned char", nil, nil, |
|||
"unsigned char", nil, nil], |
|||
["PBYTE", "unsigned char *", nil, nil, |
|||
"unsigned char *", nil, nil], |
|||
["UINT", "unsigned int", nil, nil, |
|||
"unsigned int", nil, nil], |
|||
["ULONG", "unsigned long", nil, nil, |
|||
"unsigned long", nil, nil], |
|||
["UCHAR", "unsigned char", nil, nil, |
|||
"unsigned char", nil, nil], |
|||
["HANDLE", "unsigned long", nil, nil, |
|||
"unsigned long", nil, nil], |
|||
["PHANDLE","void*", nil, nil, |
|||
"void*", nil, nil], |
|||
["PVOID", "void*", nil, nil, |
|||
"void*", nil, nil], |
|||
["LPCSTR", "char*", nil, nil, |
|||
"char*", nil, nil], |
|||
["HDC", "unsigned int", nil, nil, |
|||
"unsigned int", nil, nil], |
|||
["HWND", "unsigned int", nil, nil, |
|||
"unsigned int", nil, nil], |
|||
|
|||
# Others |
|||
["uint", "unsigned int", nil, nil, |
|||
"unsigned int", nil, nil], |
|||
["u_int", "unsigned int", nil, nil, |
|||
"unsigned int", nil, nil], |
|||
["ulong", "unsigned long", nil, nil, |
|||
"unsigned long", nil, nil], |
|||
["u_long", "unsigned long", nil, nil, |
|||
"unsigned long", nil, nil], |
|||
|
|||
# DL::Importable primitive types |
|||
["ibool", |
|||
"I", |
|||
proc{|v| v ? 1 : 0}, |
|||
proc{|v| (v != 0) ? true : false}, |
|||
"I", |
|||
proc{|v| v ? 1 : 0 }, |
|||
proc{|v| (v != 0) ? true : false} ], |
|||
["cbool", |
|||
"C", |
|||
proc{|v| v ? 1 : 0}, |
|||
proc{|v| (v != 0) ? true : false}, |
|||
"C", |
|||
proc{|v,len| v ? 1 : 0}, |
|||
proc{|v,len| (v != 0) ? true : false}], |
|||
["lbool", |
|||
"L", |
|||
proc{|v| v ? 1 : 0}, |
|||
proc{|v| (v != 0) ? true : false}, |
|||
"L", |
|||
proc{|v,len| v ? 1 : 0}, |
|||
proc{|v,len| (v != 0) ? true : false}], |
|||
["unsigned char", |
|||
"C", |
|||
proc{|v| [v].pack("C").unpack("c")[0]}, |
|||
proc{|v| [v].pack("c").unpack("C")[0]}, |
|||
"C", |
|||
proc{|v| [v].pack("C").unpack("c")[0]}, |
|||
proc{|v| [v].pack("c").unpack("C")[0]}], |
|||
["unsigned short", |
|||
"H", |
|||
proc{|v| [v].pack("S").unpack("s")[0]}, |
|||
proc{|v| [v].pack("s").unpack("S")[0]}, |
|||
"H", |
|||
proc{|v| [v].pack("S").unpack("s")[0]}, |
|||
proc{|v| [v].pack("s").unpack("S")[0]}], |
|||
["unsigned int", |
|||
"I", |
|||
proc{|v| [v].pack("I").unpack("i")[0]}, |
|||
proc{|v| [v].pack("i").unpack("I")[0]}, |
|||
"I", |
|||
proc{|v| [v].pack("I").unpack("i")[0]}, |
|||
proc{|v| [v].pack("i").unpack("I")[0]}], |
|||
["unsigned long", |
|||
"L", |
|||
proc{|v| [v].pack("L").unpack("l")[0]}, |
|||
proc{|v| [v].pack("l").unpack("L")[0]}, |
|||
"L", |
|||
proc{|v| [v].pack("L").unpack("l")[0]}, |
|||
proc{|v| [v].pack("l").unpack("L")[0]}], |
|||
["unsigned char ref", |
|||
"c", |
|||
proc{|v| [v].pack("C").unpack("c")[0]}, |
|||
proc{|v| [v].pack("c").unpack("C")[0]}, |
|||
nil, nil, nil], |
|||
["unsigned int ref", |
|||
"i", |
|||
proc{|v| [v].pack("I").unpack("i")[0]}, |
|||
proc{|v| [v].pack("i").unpack("I")[0]}, |
|||
nil, nil, nil], |
|||
["unsigned long ref", |
|||
"l", |
|||
proc{|v| [v].pack("L").unpack("l")[0]}, |
|||
proc{|v| [v].pack("l").unpack("L")[0]}, |
|||
nil, nil, nil], |
|||
["char ref", "c", nil, nil, |
|||
nil, nil, nil], |
|||
["short ref", "h", nil, nil, |
|||
nil, nil, nil], |
|||
["int ref", "i", nil, nil, |
|||
nil, nil, nil], |
|||
["long ref", "l", nil, nil, |
|||
nil, nil, nil], |
|||
["float ref", "f", nil, nil, |
|||
nil, nil, nil], |
|||
["double ref","d", nil, nil, |
|||
nil, nil, nil], |
|||
["char", "C", nil, nil, |
|||
"C", nil, nil], |
|||
["short", "H", nil, nil, |
|||
"H", nil, nil], |
|||
["int", "I", nil, nil, |
|||
"I", nil, nil], |
|||
["long", "L", nil, nil, |
|||
"L", nil, nil], |
|||
["float", "F", nil, nil, |
|||
"F", nil, nil], |
|||
["double", "D", nil, nil, |
|||
"D", nil, nil], |
|||
[/^char\s*\*$/,"s",nil, nil, |
|||
"S",nil, nil], |
|||
[/^const char\s*\*$/,"S",nil, nil, |
|||
"S",nil, nil], |
|||
[/^.+\*$/, "P", nil, nil, |
|||
"P", nil, nil], |
|||
[/^.+\[\]$/, "a", nil, nil, |
|||
"a", nil, nil], |
|||
["void", "0", nil, nil, |
|||
nil, nil, nil], |
|||
] |
|||
|
|||
def initialize |
|||
init_types() |
|||
end |
|||
|
|||
def typealias(ty1, ty2, enc=nil, dec=nil, ty3=nil, senc=nil, sdec=nil) |
|||
@TYDEFS.unshift([ty1, ty2, enc, dec, ty3, senc, sdec]) |
|||
end |
|||
|
|||
def init_types |
|||
@TYDEFS = TYPES.dup |
|||
end |
|||
|
|||
def encode_argument_type(alias_type) |
|||
proc_encode = nil |
|||
proc_decode = nil |
|||
@TYDEFS.each{|aty,ty,enc,dec,_,_,_| |
|||
if( (aty.is_a?(Regexp) && (aty =~ alias_type)) || (aty == alias_type) ) |
|||
alias_type = alias_type.gsub(aty,ty) if ty |
|||
alias_type.strip! if alias_type |
|||
if( proc_encode ) |
|||
if( enc ) |
|||
conv1 = proc_encode |
|||
proc_encode = proc{|v| enc.call(conv1.call(v))} |
|||
end |
|||
else |
|||
if( enc ) |
|||
proc_encode = enc |
|||
end |
|||
end |
|||
if( proc_decode ) |
|||
if( dec ) |
|||
conv2 = proc_decode |
|||
proc_decode = proc{|v| dec.call(conv2.call(v))} |
|||
end |
|||
else |
|||
if( dec ) |
|||
proc_decode = dec |
|||
end |
|||
end |
|||
end |
|||
} |
|||
return [alias_type, proc_encode, proc_decode] |
|||
end |
|||
|
|||
def encode_return_type(ty) |
|||
ty, enc, dec = encode_argument_type(ty) |
|||
return [ty, enc, dec] |
|||
end |
|||
|
|||
def encode_struct_type(alias_type) |
|||
proc_encode = nil |
|||
proc_decode = nil |
|||
@TYDEFS.each{|aty,_,_,_,ty,enc,dec| |
|||
if( (aty.is_a?(Regexp) && (aty =~ alias_type)) || (aty == alias_type) ) |
|||
alias_type = alias_type.gsub(aty,ty) if ty |
|||
alias_type.strip! if alias_type |
|||
if( proc_encode ) |
|||
if( enc ) |
|||
conv1 = proc_encode |
|||
proc_encode = proc{|v| enc.call(conv1.call(v))} |
|||
end |
|||
else |
|||
if( enc ) |
|||
proc_encode = enc |
|||
end |
|||
end |
|||
if( proc_decode ) |
|||
if( dec ) |
|||
conv2 = proc_decode |
|||
proc_decode = proc{|v| dec.call(conv2.call(v))} |
|||
end |
|||
else |
|||
if( dec ) |
|||
proc_decode = dec |
|||
end |
|||
end |
|||
end |
|||
} |
|||
return [alias_type, proc_encode, proc_decode] |
|||
end |
|||
end # end of Types |
|||
end |
|||
@ -0,0 +1,25 @@ |
|||
# -*- ruby -*- |
|||
|
|||
require 'dl' |
|||
|
|||
class Win32API |
|||
DLL = {} |
|||
|
|||
def initialize(dllname, func, import, export = "0") |
|||
prototype = (export + import.to_s).tr("VPpNnLlIi", "0SSI").sub(/^(.)0*$/, '\1') |
|||
handle = DLL[dllname] ||= DL::Handle.new(dllname) |
|||
@sym = handle.sym(func, prototype) |
|||
end |
|||
|
|||
def call(*args) |
|||
import = @sym.proto.split("", 2)[1] |
|||
args.each_with_index do |x, i| |
|||
args[i] = nil if x == 0 and import[i] == ?S |
|||
args[i], = [x].pack("I").unpack("i") if import[i] == ?I |
|||
end |
|||
ret, = @sym.call(*args) |
|||
return ret || 0 |
|||
end |
|||
|
|||
alias Call call |
|||
end |
|||
@ -0,0 +1,2 @@ |
|||
require 'drb/drb' |
|||
|
|||
@ -0,0 +1,146 @@ |
|||
# acl-2.0 - simple Access Control List |
|||
# |
|||
# Copyright (c) 2000,2002,2003 Masatoshi SEKI |
|||
# |
|||
# acl.rb is copyrighted free software by Masatoshi SEKI. |
|||
# You can redistribute it and/or modify it under the same terms as Ruby. |
|||
|
|||
require 'ipaddr' |
|||
|
|||
class ACL |
|||
VERSION=["2.0.0"] |
|||
class ACLEntry |
|||
def initialize(str) |
|||
if str == '*' or str == 'all' |
|||
@pat = [:all] |
|||
elsif str.include?('*') |
|||
@pat = [:name, dot_pat(str)] |
|||
else |
|||
begin |
|||
@pat = [:ip, IPAddr.new(str)] |
|||
rescue ArgumentError |
|||
@pat = [:name, dot_pat(str)] |
|||
end |
|||
end |
|||
end |
|||
|
|||
private |
|||
def dot_pat_str(str) |
|||
list = str.split('.').collect { |s| |
|||
(s == '*') ? '.+' : s |
|||
} |
|||
list.join("\\.") |
|||
end |
|||
|
|||
private |
|||
def dot_pat(str) |
|||
exp = "^" + dot_pat_str(str) + "$" |
|||
Regexp.new(exp) |
|||
end |
|||
|
|||
public |
|||
def match(addr) |
|||
case @pat[0] |
|||
when :all |
|||
true |
|||
when :ip |
|||
begin |
|||
ipaddr = IPAddr.new(addr[3]) |
|||
ipaddr = ipaddr.ipv4_mapped if @pat[1].ipv6? && ipaddr.ipv4? |
|||
rescue ArgumentError |
|||
return false |
|||
end |
|||
(@pat[1].include?(ipaddr)) ? true : false |
|||
when :name |
|||
(@pat[1] =~ addr[2]) ? true : false |
|||
else |
|||
false |
|||
end |
|||
end |
|||
end |
|||
|
|||
class ACLList |
|||
def initialize |
|||
@list = [] |
|||
end |
|||
|
|||
public |
|||
def match(addr) |
|||
@list.each do |e| |
|||
return true if e.match(addr) |
|||
end |
|||
false |
|||
end |
|||
|
|||
public |
|||
def add(str) |
|||
@list.push(ACLEntry.new(str)) |
|||
end |
|||
end |
|||
|
|||
DENY_ALLOW = 0 |
|||
ALLOW_DENY = 1 |
|||
|
|||
def initialize(list=nil, order = DENY_ALLOW) |
|||
@order = order |
|||
@deny = ACLList.new |
|||
@allow = ACLList.new |
|||
install_list(list) if list |
|||
end |
|||
|
|||
public |
|||
def allow_socket?(soc) |
|||
allow_addr?(soc.peeraddr) |
|||
end |
|||
|
|||
public |
|||
def allow_addr?(addr) |
|||
case @order |
|||
when DENY_ALLOW |
|||
return true if @allow.match(addr) |
|||
return false if @deny.match(addr) |
|||
return true |
|||
when ALLOW_DENY |
|||
return false if @deny.match(addr) |
|||
return true if @allow.match(addr) |
|||
return false |
|||
else |
|||
false |
|||
end |
|||
end |
|||
|
|||
public |
|||
def install_list(list) |
|||
i = 0 |
|||
while i < list.size |
|||
permission, domain = list.slice(i,2) |
|||
case permission.downcase |
|||
when 'allow' |
|||
@allow.add(domain) |
|||
when 'deny' |
|||
@deny.add(domain) |
|||
else |
|||
raise "Invalid ACL entry #{list.to_s}" |
|||
end |
|||
i += 2 |
|||
end |
|||
end |
|||
end |
|||
|
|||
if __FILE__ == $0 |
|||
# example |
|||
list = %w(deny all |
|||
allow 192.168.1.1 |
|||
allow ::ffff:192.168.1.2 |
|||
allow 192.168.1.3 |
|||
) |
|||
|
|||
addr = ["AF_INET", 10, "lc630", "192.168.1.3"] |
|||
|
|||
acl = ACL.new |
|||
p acl.allow_addr?(addr) |
|||
|
|||
acl = ACL.new(list, ACL::DENY_ALLOW) |
|||
p acl.allow_addr?(addr) |
|||
end |
|||
|
|||
Some files were not shown because too many files changed in this diff
Loading…
Reference in new issue